(root)/
gcc-13.2.0/
libffi/
testsuite/
libffi.call/
pr1172638.c
       1  /* Area:	ffi_call
       2     Purpose:	Reproduce bug found in python ctypes
       3     Limitations:	none.
       4     PR:		Fedora 1174037  */
       5  
       6  /* { dg-do run } */
       7  #include "ffitest.h"
       8  
       9  typedef struct {
      10    long x;
      11    long y;
      12  } POINT;
      13  
      14  typedef struct {
      15    long left;
      16    long top;
      17    long right;
      18    long bottom;
      19  } RECT;
      20  
      21  static RECT ABI_ATTR pr_test(int i __UNUSED__, RECT ar __UNUSED__, 
      22  			     RECT* br __UNUSED__, POINT cp __UNUSED__, 
      23  			     RECT dr __UNUSED__, RECT *er __UNUSED__, 
      24  			     POINT fp, RECT gr __UNUSED__)
      25  {
      26    RECT result;
      27  
      28    result.left = fp.x;
      29    result.right = fp.y;
      30    result.top = fp.x;
      31    result.bottom = fp.y;
      32  
      33    return result;
      34  }
      35  
      36  int main (void)
      37  {
      38    ffi_cif cif;
      39    ffi_type *args[MAX_ARGS];
      40    void *values[MAX_ARGS];
      41    ffi_type point_type, rect_type;
      42    ffi_type *point_type_elements[3];  
      43    ffi_type *rect_type_elements[5];  
      44    
      45    int i;
      46    POINT cp, fp;
      47    RECT ar, br, dr, er, gr; 
      48    RECT *p1, *p2;
      49  
      50    /* This is a hack to get a properly aligned result buffer */
      51    RECT *rect_result =
      52      (RECT *) malloc (sizeof(RECT));
      53  
      54    point_type.size = 0;
      55    point_type.alignment = 0;
      56    point_type.type = FFI_TYPE_STRUCT;
      57    point_type.elements = point_type_elements;
      58    point_type_elements[0] = &ffi_type_slong;
      59    point_type_elements[1] = &ffi_type_slong;
      60    point_type_elements[2] = NULL;
      61  
      62    rect_type.size = 0;
      63    rect_type.alignment = 0;
      64    rect_type.type = FFI_TYPE_STRUCT;
      65    rect_type.elements = rect_type_elements;
      66    rect_type_elements[0] = &ffi_type_slong;
      67    rect_type_elements[1] = &ffi_type_slong;
      68    rect_type_elements[2] = &ffi_type_slong;
      69    rect_type_elements[3] = &ffi_type_slong;
      70    rect_type_elements[4] = NULL;
      71  
      72    args[0] = &ffi_type_sint;
      73    args[1] = &rect_type;
      74    args[2] = &ffi_type_pointer;
      75    args[3] = &point_type;
      76    args[4] = &rect_type;
      77    args[5] = &ffi_type_pointer;
      78    args[6] = &point_type;
      79    args[7] = &rect_type;
      80    
      81    /* Initialize the cif */
      82    CHECK(ffi_prep_cif(&cif, ABI_NUM, 8, &rect_type, args) == FFI_OK);
      83  
      84    i = 1;
      85    ar.left = 2;
      86    ar.right = 3;
      87    ar.top = 4;
      88    ar.bottom = 5;
      89    br.left = 6;
      90    br.right = 7;
      91    br.top = 8;
      92    br.bottom = 9;
      93    cp.x = 10;
      94    cp.y = 11;
      95    dr.left = 12;
      96    dr.right = 13;
      97    dr.top = 14;
      98    dr.bottom = 15;
      99    er.left = 16;
     100    er.right = 17;
     101    er.top = 18;
     102    er.bottom = 19;
     103    fp.x = 20;
     104    fp.y = 21;
     105    gr.left = 22;
     106    gr.right = 23;
     107    gr.top = 24;
     108    gr.bottom = 25;
     109    
     110    values[0] = &i;
     111    values[1] = &ar;
     112    p1 = &br;
     113    values[2] = &p1;
     114    values[3] = &cp;
     115    values[4] = &dr;
     116    p2 = &er;
     117    values[5] = &p2;
     118    values[6] = &fp;
     119    values[7] = &gr;
     120  
     121    ffi_call (&cif, FFI_FN(pr_test), rect_result, values);
     122    
     123    CHECK(rect_result->top == 20);
     124   
     125    free (rect_result);
     126    exit(0);
     127  }