Skip to content

Commit

Permalink
another option(still not working)
Browse files Browse the repository at this point in the history
  • Loading branch information
aodinokov committed Aug 17, 2024
1 parent 69e8d8d commit 08d276a
Show file tree
Hide file tree
Showing 2 changed files with 46 additions and 9 deletions.
39 changes: 34 additions & 5 deletions examples/c_ffi_call/value_ffi.c
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,32 @@ static int _val_to_ffi_type(metac_entry_t * p_entry, metac_flag_t variadic, ffi_
_process_(long, ffi_type_slong);
_process_(long long, ffi_type_slong);
#undef _process_
} else if (
metac_entry_is_va_list_parameter(p_entry) != 0 ) {
ffi_type * p_ffi_type = calloc(1, sizeof(ffi_type));
if (p_ffi_type == NULL) {
return -ENOMEM;
}
#if __linux__
p_ffi_type->alignment = 0;
p_ffi_type->type = FFI_TYPE_STRUCT;
p_ffi_type->size = sizeof(va_list);
p_ffi_type->elements = calloc(sizeof(ffi_type)/sizeof(void*) + 1 /* for NULL */, sizeof(ffi_type *));
if (p_ffi_type->elements == NULL) {
free(p_ffi_type);
return -(ENOMEM);
}
for (int i = 0; i < sizeof(ffi_type)/sizeof(void*); ++i) {
p_ffi_type->elements[i] = calloc(1, sizeof(ffi_type));
if (p_ffi_type->elements[i] != NULL) {
memcpy(p_ffi_type->elements[i], &ffi_type_pointer, sizeof(ffi_type));
}
}
#else
memcpy(p_ffi_type, &ffi_type_pointer, sizeof(ffi_type));
#endif
*pp_rtype = p_ffi_type;
return 0;
} else if (
metac_entry_is_pointer(p_entry) != 0) {
ffi_type * p_ffi_type = calloc(1, sizeof(ffi_type));
Expand All @@ -110,11 +136,9 @@ static int _val_to_ffi_type(metac_entry_t * p_entry, metac_flag_t variadic, ffi_
*pp_rtype = p_ffi_type;
return 0;
} else if (
metac_entry_is_va_list_parameter(p_entry) != 0 || // TODO: to check
(
variadic != 0 && (
metac_entry_has_members(p_entry) != 0 ||
metac_entry_has_elements(p_entry) != 0))) {
metac_entry_has_elements(p_entry) != 0)) {
ffi_type * p_ffi_type = calloc(1, sizeof(ffi_type));
if (p_ffi_type == NULL) {
return -ENOMEM;
Expand Down Expand Up @@ -223,7 +247,7 @@ static int _val_to_ffi_type(metac_entry_t * p_entry, metac_flag_t variadic, ffi_
bitfield_state = 0;

if (_val_to_ffi_type(p_memb_entry, variadic, &p_tmp->elements[memb_id]) != 0) {
free(p_tmp->elements);
free(p_tmp->elements); // TODO: cleanup _tmp->elements prior to
free(p_tmp);
return -(EFAULT);
}
Expand Down Expand Up @@ -437,7 +461,12 @@ int _call(metac_value_t * p_param_storage_val, void (*fn)(void), metac_value_t *
} else {
assert(va_list_number_cur < va_list_number);
assert(p_val_list_entries[va_list_number_cur].id == i);
values[i] = &p_val_list_entries[va_list_number_cur].va_list_c;
#if __linux__
values[i] = &p_val_list_entries[va_list_number_cur].va_list_c.parameters;
#else
va_list * x = &p_val_list_entries[va_list_number_cur].va_list_c;
values[i] = x;
#endif
++va_list_number_cur;
// // simple approach (without recursion)
// assert(metac_value_has_parameter_load(p_param_val));
Expand Down
16 changes: 12 additions & 4 deletions examples/c_ffi_call/value_ffi_test.c
Original file line number Diff line number Diff line change
Expand Up @@ -623,14 +623,20 @@ METAC_START_TEST(test_function_with_extra) {

// variadic param tests
int test_function_with_va_list(const char * format, va_list vl) {
// va_list l;
// va_copy(l, vl);
// int i = va_arg(l, int);
// va_end(l);

return vsnprintf(called, sizeof(called), format, vl);
// return 0;
}
METAC_GSYM_LINK(test_function_with_va_list);

int test_function_with_va_args(const char * format, ...) {
va_list l;
va_start(l, format);
int res = test_function_with_va_list(format, l);
int res = vsnprintf(called, sizeof(called), format, l);
va_end(l);
return res;
}
Expand Down Expand Up @@ -786,14 +792,16 @@ METAC_START_TEST(test_variadic_list) {
{
called[0] = 0;
metac_entry_t * p_entry = METAC_GSYM_LINK_ENTRY(test_function_with_va_list);
metac_value_t * p_params_val = METAC_NEW_VALUE_WITH_CALL_PARAMS_AND_WRAP(p_tagmap, p_entry, test_function_with_va_list, "test_function_with_va_list %d", VA_LIST(777));
metac_value_t * p_params_val = METAC_NEW_VALUE_WITH_CALL_PARAMS_AND_WRAP(p_tagmap, p_entry,
test_function_with_va_list, "test_function_with_va_list %x %x %x %x %x %x", VA_LIST(1,2,3,4,5,6));
metac_value_t *p_res_val = metac_new_value_with_call_result(p_entry);
int res = metac_value_call(p_params_val, (void (*)(void)) test_function_with_va_list, p_res_val);

expected = "test_function_with_va_list(\"test_function_with_va_list %d\", VA_LIST((int)777))";
expected = "test_function_with_va_list(\"test_function_with_va_list %x %x %x %x %x %x\", "
"VA_LIST((unsigned int)1, (unsigned int)2, (unsigned int)3, (unsigned int)4, (unsigned int)5, (unsigned int)6))";
s = metac_value_string_ex(p_params_val, METAC_WMODE_deep, p_tagmap);
fail_unless(s != NULL);
//fail_unless(strcmp(s, expected) == 0, "got %s, expected %s", s, expected);
fail_unless(strcmp(s, expected) == 0, "got %s, expected %s", s, expected);
free(s);

fail_unless(res == 0, "Call wasn't successful, expected successful");
Expand Down

0 comments on commit 08d276a

Please sign in to comment.