(root)/
gcc-13.2.0/
gcc/
testsuite/
gcc.target/
powerpc/
pr89765-mc.c
       1  /* { dg-do run { target int128 } } */
       2  /* { dg-require-effective-target vsx_hw } */
       3  /* { dg-options "-mvsx -O2" } */
       4  
       5  /* This test should run the same on any target that supports vsx
       6     instructions.  Intentionally not specifying cpu in order to test
       7     all code generation paths.  */
       8  
       9  #include <stdlib.h>
      10  #include <stddef.h>
      11  #include <altivec.h>
      12  
      13  #include <stdio.h>
      14  
      15  static vector unsigned __int128
      16  deoptimize_uint128 (vector unsigned __int128  a)
      17  {
      18    __asm__ (" # %x0" : "+v" (a));
      19    return a;
      20  }
      21  
      22  static vector unsigned long long int
      23  deoptimize_ulong (vector unsigned long long int a)
      24  {
      25    __asm__ (" # %x0" : "+v" (a));
      26    return a;
      27  }
      28  
      29  static vector unsigned int
      30  deoptimize_uint (vector unsigned int a)
      31  {
      32    __asm__ (" # %x0" : "+v" (a));
      33    return a;
      34  }
      35  
      36  static vector unsigned char
      37  deoptimize_uchar (vector unsigned char a)
      38  {
      39    __asm__ (" # %x0" : "+v" (a));
      40    return a;
      41  }
      42  
      43  static vector unsigned short
      44  deoptimize_ushort (vector unsigned short a)
      45  {
      46    __asm__ (" # %x0" : "+v" (a));
      47    return a;
      48  }
      49  
      50  __attribute ((noinline))
      51  vector unsigned __int128
      52  set_auto_n_uint128 (vector unsigned __int128 a, int n, unsigned __int128 x)
      53  {
      54    return vec_insert (x, a, n);
      55  }
      56  
      57  __attribute ((noinline))
      58  vector unsigned long long int
      59  set_auto_n_ulong (vector unsigned long long int a, int n,
      60  		  unsigned long long int x)
      61  {
      62    return vec_insert (x, a, n);
      63  }
      64  
      65  __attribute ((noinline))
      66  vector unsigned int
      67  set_auto_n_uint (vector unsigned int a, int n, unsigned int x)
      68  {
      69    return vec_insert (x, a, n);
      70  }
      71  
      72  __attribute ((noinline))
      73  vector unsigned char
      74  set_auto_n_uchar (vector unsigned char a, int n, unsigned char x)
      75  {
      76    return vec_insert (x, a, n);
      77  }
      78  
      79  __attribute ((noinline))
      80  vector unsigned short
      81  set_auto_n_ushort (vector unsigned short a, int n, unsigned short x)
      82  {
      83    return vec_insert (x, a, n);
      84  }
      85  
      86  __attribute ((noinline))
      87  unsigned __int128
      88  get_auto_n_uint128 (vector unsigned __int128 a, int n)
      89  {
      90    return vec_extract (a, n);
      91  }
      92  
      93  __attribute ((noinline))
      94  unsigned long long int
      95  get_auto_n_ulong (vector unsigned long long int a, int n)
      96  {
      97    return vec_extract (a, n);
      98  }
      99  
     100  __attribute ((noinline))
     101  unsigned int
     102  get_auto_n_uint (vector unsigned int a, int n)
     103  {
     104    return vec_extract (a, n);
     105  }
     106  
     107  __attribute ((noinline))
     108  unsigned char
     109  get_auto_n_uchar (vector unsigned char a, int n)
     110  {
     111    return vec_extract (a, n);
     112  }
     113  
     114  __attribute ((noinline))
     115  unsigned short
     116  get_auto_n_ushort (vector unsigned short a, int n)
     117  {
     118    return vec_extract (a, n);
     119  }
     120  
     121  int check_uint128_element (int i, unsigned __int128 entry)
     122  {
     123    printf ("checking uint128 entry at index %d\n", i);
     124  
     125    return (entry == ((((unsigned __int128) 0xffeeddccbbaa9988ULL) << 64)
     126  		    | 0x0706050403020100ULL));
     127  }
     128  
     129  unsigned __int128 get_uint128_element (int i)
     130  {
     131    return ((((unsigned __int128) 0xffeeddccbbaa9988ULL) << 64)
     132  	  | 0x0706050403020100ULL);
     133  }
     134  
     135  int check_ulong_element (int i, unsigned long long int entry)
     136  {
     137    printf ("checking ulong entry 0x%llx at index %d\n", entry, i);
     138  
     139    switch (i % 2)
     140      {
     141        case 0: return (entry == 0x9999901010ULL);
     142        case 1: return (entry == 0x7777733333ULL);
     143        default:
     144  	return 0;
     145      }
     146  }
     147  
     148  unsigned long long int get_ulong_element (int i)
     149  {
     150    switch (i % 2)
     151      {
     152      case 0: return 0x9999901010ULL;
     153      case 1: return 0x7777733333ULL;
     154      }
     155  }
     156  
     157  int check_uint_element (int i, unsigned int entry)
     158  {
     159    printf ("checking uint entry 0x%x at index %d\n", entry, i);
     160  
     161    switch (i % 4)
     162      {
     163      case 0: return (entry == 0x99999);
     164      case 1: return (entry == 0x01010);
     165      case 2: return (entry == 0x77777);
     166      case 3: return (entry == 0x33333);
     167      default:
     168        return 0;
     169      }
     170  }
     171  
     172  unsigned int get_uint_element (int i)
     173  {
     174    switch (i % 4)
     175      {
     176      case 0: return 0x99999;
     177      case 1: return 0x01010;
     178      case 2: return 0x77777;
     179      case 3: return 0x33333;
     180      }
     181  }
     182  
     183  int check_uchar_element (int i, unsigned char entry)
     184  {
     185    printf ("checking uchar entry 0x%x at index %d\n", entry, i);
     186    switch (i % 16)
     187      {
     188      case 0: return (entry == 0x90);
     189      case 1: return (entry == 0x80);
     190      case 2: return (entry == 0x70);
     191      case 3: return (entry == 0x60);
     192      case 4: return (entry == 0x50);
     193      case 5: return (entry == 0x40);
     194      case 6: return (entry == 0x30);
     195      case 7: return (entry == 0x20);
     196      case 8: return (entry == 0x10);
     197      case 9: return (entry == 0xf0);
     198      case 10: return (entry == 0xe0);
     199      case 11: return (entry == 0xd0);
     200      case 12: return (entry == 0xc0);
     201      case 13: return (entry == 0xb0);
     202      case 14: return (entry == 0xa0);
     203      case 15: return (entry == 0xff);
     204      default:
     205        return 0;
     206      }
     207  }
     208  
     209  unsigned char get_uchar_element (int i)
     210  {
     211    switch (i % 16)
     212      {
     213      case 0: return 0x90;
     214      case 1: return 0x80;
     215      case 2: return 0x70;
     216      case 3: return 0x60;
     217      case 4: return 0x50;
     218      case 5: return 0x40;
     219      case 6: return 0x30;
     220      case 7: return 0x20;
     221      case 8: return 0x10;
     222      case 9: return 0xf0;
     223      case 10: return 0xe0;
     224      case 11: return 0xd0;
     225      case 12: return 0xc0;
     226      case 13: return 0xb0;
     227      case 14: return 0xa0;
     228      case 15: return 0xff;
     229      }
     230  }
     231  
     232  int check_ushort_element (int i, unsigned short entry)
     233  {
     234    printf ("checking ushort entry 0x%x at index %d\n", entry, i);
     235    switch (i % 8)
     236      {
     237      case 0: return (entry == 0x9988);
     238      case 1: return (entry == 0x8877);
     239      case 2: return (entry == 0x7766);
     240      case 3: return (entry == 0x6655);
     241      case 4: return (entry == 0x5544);
     242      case 5: return (entry == 0x4433);
     243      case 6: return (entry == 0x3322);
     244      case 7: return (entry == 0x2211);
     245      default:
     246        return 0;
     247      }
     248  }
     249  
     250  unsigned short get_ushort_element (int i)
     251  {
     252    switch (i % 8)
     253      {
     254      case 0: return 0x9988;
     255      case 1: return 0x8877;
     256      case 2: return 0x7766;
     257      case 3: return 0x6655;
     258      case 4: return 0x5544;
     259      case 5: return 0x4433;
     260      case 6: return 0x3322;
     261      case 7: return 0x2211;
     262      }
     263  }
     264  
     265  vector unsigned __int128
     266  init_auto_uint128 (vector unsigned __int128 a)
     267  {
     268    int i;
     269    for (i = 0; i < 32; i += 3)
     270      a = set_auto_n_uint128 (a, i, get_uint128_element (i));
     271    return a;
     272  }
     273  
     274  void do_auto_uint128 (vector unsigned __int128 a)
     275  {
     276    int i;
     277    unsigned __int128 c;
     278    for (i = 0; i < 32; i += 3)
     279      {
     280        c = get_auto_n_uint128 (a, i);
     281        if (!check_uint128_element (i, c)) abort ();
     282      }
     283  }
     284  
     285  vector unsigned long long int
     286  init_auto_ulong (vector unsigned long long int a)
     287  {
     288    int i;
     289    for (i = 0; i < 32; i += 3)
     290      a = set_auto_n_ulong (a, i, get_ulong_element (i));
     291    return a;
     292  }
     293  
     294  void do_auto_ulong (vector unsigned long long int a)
     295  {
     296    int i;
     297    unsigned long long int c;
     298    for (i = 0; i < 32; i += 3)
     299      {
     300        c = get_auto_n_ulong (a, i);
     301        if (!check_ulong_element (i, c)) abort ();
     302      }
     303   }
     304  
     305  vector unsigned int init_auto_uint (vector unsigned int a)
     306  {
     307    int i;
     308    for (i = 0; i < 32; i += 3)
     309      a = set_auto_n_uint (a, i, get_uint_element (i));
     310    return a;
     311  }
     312  
     313  void do_auto_uint (vector unsigned int a)
     314  {
     315    int i;
     316    unsigned int c;
     317    for (i = 0; i < 32; i += 3)
     318      {
     319        c = get_auto_n_uint (a, i);
     320        if (!check_uint_element (i, c)) abort ();
     321      }
     322   }
     323  
     324  vector unsigned short init_auto_ushort ( vector unsigned short a )
     325  {
     326    int i;
     327    for (i = 0; i < 32; i += 3)
     328      a = set_auto_n_ushort (a, i, get_ushort_element (i));
     329    return a;
     330  }
     331  
     332  void do_auto_ushort (vector unsigned short a)
     333  {
     334    int i;
     335    unsigned short c;
     336    for (i = 0; i < 32; i += 3)
     337      {
     338        c = get_auto_n_ushort (a, i);
     339        if (!check_ushort_element (i, c)) abort ();
     340      }
     341  }
     342  
     343  vector unsigned char init_auto_uchar (vector unsigned char a)
     344  {
     345    int i;
     346    for (i = 0; i < 32; i += 3)
     347      a = set_auto_n_uchar (a, i, get_uchar_element (i));
     348    return a;
     349  }
     350  
     351  void do_auto_uchar (vector unsigned char a)
     352  {
     353    int i;
     354    unsigned char c;
     355    for (i = 0; i < 32; i += 3)
     356      {
     357        c = get_auto_n_uchar (a, i);
     358        if (!check_uchar_element (i, c)) abort ();
     359      }
     360  }
     361  
     362  int
     363  main (void)
     364  {
     365    size_t i;
     366  
     367    vector unsigned __int128 u = { 0 };
     368    vector unsigned __int128 du;
     369  
     370    vector unsigned long long int v = { 0, 0 };
     371    vector unsigned long long int dv;
     372  
     373    vector unsigned int x = { 0, 0, 0, 0 };
     374    vector unsigned int dx;
     375  
     376    vector unsigned char y = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
     377    vector unsigned char dy;
     378  
     379    vector unsigned short z = { 0, 0, 0, 0, 0, 0, 0, 0 };
     380    vector unsigned short dz;
     381  
     382    du = init_auto_uint128 (u);
     383    dv = init_auto_ulong (v);
     384    dx = init_auto_uint (x);
     385    dy = init_auto_uchar (y);
     386    dz = init_auto_ushort (z);
     387  
     388    du = deoptimize_uint128 (du);
     389    dv = deoptimize_ulong (dv);
     390    dx = deoptimize_uint (dx);
     391    dy = deoptimize_uchar (dy);
     392    dz = deoptimize_ushort (dz);
     393  
     394    do_auto_uint128 (du);
     395    do_auto_ulong (dv);
     396    do_auto_uint (dx);
     397    do_auto_uchar (dy);
     398    do_auto_ushort (dz);
     399    return 0;
     400  }