Ejemplo n.º 1
0
int main(int argc, char **argv) {
   int i;
   vector unsigned int all_ones = (vector unsigned int) 
      {0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF};

   vector unsigned int all_zeroes = (vector unsigned int) 
      {0x00000000, 0x00000000, 0x00000000, 0x00000000};
   
   /* These bits will form the selection mask */
   unsigned short mask = 0x9;
   
   /* Each bit in 0x9 forms a word in the mask */
   vector unsigned int resultw = 
      spu_sel(all_zeroes, all_ones, spu_maskw(mask));
   printf("resultw: ");
   for (i=0; i<4; i++) {
      printf("%08x", spu_extract(resultw, i));
   }
   
   /* Each bit in 0x09 forms a halfword in the mask */
   vector unsigned short resulth = 
      spu_sel((vector unsigned short)all_zeroes, 
              (vector unsigned short)all_ones, 
              spu_maskh(mask));
   printf("\nresulth: ");
   for (i=0; i<8; i++) {
      printf("%04x", spu_extract(resulth, i));
   }

   /* Each bit in 0x0009 forms a byte in the mask */
   vector unsigned char resultb = 
      spu_sel((vector unsigned char)all_zeroes, 
              (vector unsigned char)all_ones, 
              spu_maskb(mask));
   printf("\nresultb: ");
   for (i=0; i<16; i++) {
      printf("%02x", spu_extract(resultb, i));
   }
   printf("\n");
   return 0;
}
Ejemplo n.º 2
0
/* Scans the string pointed to by s for the character c and
 * returns a pointer to the last occurance of c. If
 * c is not found, then NULL is returned.
 */
char * strrchr(const char *s, int c)
{
  int nskip;
  vec_uchar16 *ptr, data, vc;
  vec_uint4 cmp_c, cmp_0, cmp;
  vec_uint4 res_ptr, res_cmp;
  vec_uint4 mask, result;
  vec_uint4 one = spu_splats(0xffffU);
  /* Scan memory array a quadword at a time. Skip leading
   * mis-aligned bytes.
   */
  ptr = (vec_uchar16 *)s;

  nskip = -((unsigned int)(ptr) & 15);
  mask = spu_rlmask(one, nskip);

  vc = spu_splats((unsigned char)(c));

  data = *ptr++;
  ptr = (vec_uchar16 *)((unsigned int)ptr & ~15);

  cmp_c = spu_and(spu_gather(spu_cmpeq(data, vc)), mask);
  cmp_0 = spu_and(spu_gather(spu_cmpeq(data, 0)), mask);

  res_ptr = spu_splats(0U);
  res_cmp = spu_splats(0U);

  while (spu_extract(cmp_0, 0) == 0) {
    cmp = spu_cmpeq(cmp_c, 0);

    res_ptr = spu_sel(spu_promote((unsigned int)(ptr), 0), res_ptr, cmp);
    res_cmp = spu_sel(cmp_c, res_cmp, cmp);

    data = *ptr++;

    cmp_c = spu_gather(spu_cmpeq(data, vc));
    cmp_0 = spu_gather(spu_cmpeq(data, 0));

    cmp = spu_cmpeq(cmp_c, 0);
  }

  /* Compute the location of the last character before termination
   * character.
   *
   * First mask off compare results following the first termination character.
   */
  mask = spu_sl(one, 31 - spu_extract(spu_cntlz(cmp_0), 0));
  cmp_c = spu_and(cmp_c, mask);

  /* Conditionally update res_ptr and res_cmd if a match was found in the last
   * quadword.
   */
  cmp = spu_cmpeq(cmp_c, 0);

  res_ptr = spu_sel(spu_promote((unsigned int)(ptr), 0), res_ptr, cmp);
  res_cmp = spu_sel(cmp_c, res_cmp, cmp);

  /* Bit reserve res_cmp for locating last occurance.
   */
  mask = spu_cmpeq(res_cmp, 0);

  res_cmp = (vec_uint4)spu_maskb(spu_extract(res_cmp, 0));
  res_cmp = spu_gather((vec_uchar16)spu_shuffle(res_cmp, res_cmp,
						VEC_LITERAL(vec_uchar16,
							    15,14,13,12,11,10,9,8,7,6,5,4,3,2,1,0)));

  /* Compute the location (ptr) of the last occurance of c. If no
   * occurance was found (ie, element 0 of res_cmp == 0, then return
   * NULL.
   */
  result = spu_sub(spu_add(res_ptr, 15), spu_cntlz(res_cmp));
  result = spu_andc(result, mask);

  return ((char *)spu_extract(result, 0));
}