test-accessing-struct.c 2.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113
  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include "libgccjit.h"
  4. #include "harness.h"
  5. struct foo
  6. {
  7. int x;
  8. int y;
  9. int z;
  10. };
  11. void
  12. create_code (gcc_jit_context *ctxt, void *user_data)
  13. {
  14. /* Let's try to inject the equivalent of:
  15. void
  16. test_access (struct foo *f)
  17. {
  18. f->z = f->x * f->y;
  19. }
  20. */
  21. gcc_jit_type *void_type =
  22. gcc_jit_context_get_type (ctxt, GCC_JIT_TYPE_VOID);
  23. gcc_jit_type *int_type =
  24. gcc_jit_context_get_type (ctxt, GCC_JIT_TYPE_INT);
  25. gcc_jit_field *x =
  26. gcc_jit_context_new_field (ctxt,
  27. NULL,
  28. int_type,
  29. "x");
  30. gcc_jit_field *y =
  31. gcc_jit_context_new_field (ctxt,
  32. NULL,
  33. int_type,
  34. "y");
  35. gcc_jit_field *z =
  36. gcc_jit_context_new_field (ctxt,
  37. NULL,
  38. int_type,
  39. "z");
  40. gcc_jit_field *fields[] = {x, y, z};
  41. gcc_jit_struct *struct_type =
  42. gcc_jit_context_new_struct_type (ctxt, NULL, "foo", 3, fields);
  43. gcc_jit_type *ptr_type =
  44. gcc_jit_type_get_pointer (gcc_jit_struct_as_type (struct_type));
  45. /* Build the test function. */
  46. gcc_jit_param *param_f =
  47. gcc_jit_context_new_param (ctxt, NULL, ptr_type, "f");
  48. gcc_jit_function *test_fn =
  49. gcc_jit_context_new_function (ctxt, NULL,
  50. GCC_JIT_FUNCTION_EXPORTED,
  51. void_type,
  52. "test_access",
  53. 1, &param_f,
  54. 0);
  55. /* f->x * f->y */
  56. gcc_jit_rvalue *sum =
  57. gcc_jit_context_new_binary_op (
  58. ctxt, NULL,
  59. GCC_JIT_BINARY_OP_MULT,
  60. int_type,
  61. gcc_jit_lvalue_as_rvalue (
  62. gcc_jit_rvalue_dereference_field (
  63. gcc_jit_param_as_rvalue (param_f),
  64. NULL,
  65. x)),
  66. gcc_jit_lvalue_as_rvalue (
  67. gcc_jit_rvalue_dereference_field (
  68. gcc_jit_param_as_rvalue (param_f),
  69. NULL,
  70. y)));
  71. /* f->z = ... */
  72. gcc_jit_block *block = gcc_jit_function_new_block (test_fn, NULL);
  73. gcc_jit_block_add_assignment (
  74. block,
  75. NULL,
  76. gcc_jit_rvalue_dereference_field (
  77. gcc_jit_param_as_rvalue (param_f),
  78. NULL,
  79. z),
  80. sum);
  81. gcc_jit_block_end_with_void_return (block, NULL);
  82. }
  83. void
  84. verify_code (gcc_jit_context *ctxt, gcc_jit_result *result)
  85. {
  86. typedef void (*fn_type) (struct foo *);
  87. CHECK_NON_NULL (result);
  88. fn_type test_access =
  89. (fn_type)gcc_jit_result_get_code (result, "test_access");
  90. CHECK_NON_NULL (test_access);
  91. struct foo tmp;
  92. tmp.x = 5;
  93. tmp.y = 7;
  94. tmp.z = 0;
  95. /* Call the JIT-generated function. */
  96. test_access (&tmp);
  97. /* Verify that the code correctly modified the field "z". */
  98. CHECK_VALUE (tmp.z, 35);
  99. }