ret value must be 10 for strnlen, and 5 for u8_mbsnlen; I've slightly modified the strlen.c from testsuite/libffi.call; in the same manner I've replaced return value type ffi_type_sint with a "structured" type of the size sizeof(size_t). Test interrupts since then: $ ./a.out check new check new->elements check ffi_arg init size of the structure check 1 Aborted All right when return value of ffi_type_sint (comment out rows ##42, 45 and uncomment ##43, 46): $ ./a.out check new check new->elements check ffi_arg init size of the structure check 1 check 7 check 25 There's no problem on x86_64 as well. > tag 593558 + moreinfo > thanks > > On 19.08.2010 10:48, Ygrex wrote: > > Package: libffi-dev > > Version: 3.0.9-2 > > Severity: important > > > > The test C-code is attached: > > gcc-4.4 -lffi -lunistring -o test test.c > > > > It can be compiled without libunistring as well (see notes, please): > > 1. comment out rows #7 and #8 > > 2. uncomment #9 > > 3. gcc-4.4 -lffi -o test test.c > > > > What the code does: > > 1. creates a new ffi_type to emulate size_t; > > 2. allocates array of types of function arguments: (char *) and > > (size_t); 3. prepare CIF to call the size_t function with two > > arguments; 4. allocates array of pointers to two arguments: char *b > > and size_t a; 5. runs ffi_call and segfaults; > > unable to reproduce on i386 unstable (without the library): > > $ valgrind --track-origins=yes -q ./a.out > just before... > ==13621== Conditional jump or move depends on uninitialised value(s) > ==13621== at 0x48DC040: strnlen (mc_replace_strmem.c:263) > ==13621== by 0x48FB54E: ffi_call_SYSV > (in /usr/lib/libffi.so.5.0.10) ==13621== by 0x48FB38D: ffi_call > (in /usr/lib/libffi.so.5.0.10) ==13621== by 0x80488FC: main > (test.c:71) ==13621== Uninitialised value was created by a heap > allocation ==13621== at 0x48DAF50: malloc (vg_replace_malloc.c:236) > ==13621== by 0x8048842: main (test.c:55) > ==13621== > right after! > ==13621== Use of uninitialised value of size 4 > ==13621== at 0x49390FE: _itoa_word (_itoa.c:195) > ==13621== by 0x493C8EF: vfprintf (vfprintf.c:1613) > ==13621== by 0x4943FAF: printf (printf.c:35) > ==13621== by 0x804891F: main (test.c:80) > ==13621== Uninitialised value was created by a heap allocation > ==13621== at 0x48DAF50: malloc (vg_replace_malloc.c:236) > ==13621== by 0x8048842: main (test.c:55) > ==13621== > ==13621== Conditional jump or move depends on uninitialised value(s) > ==13621== at 0x4939106: _itoa_word (_itoa.c:195) > ==13621== by 0x493C8EF: vfprintf (vfprintf.c:1613) > ==13621== by 0x4943FAF: printf (printf.c:35) > ==13621== by 0x804891F: main (test.c:80) > ==13621== Uninitialised value was created by a heap allocation > ==13621== at 0x48DAF50: malloc (vg_replace_malloc.c:236) > ==13621== by 0x8048842: main (test.c:55) > ==13621== > ret value: 0 > -- С уважением, Igor Bogomazov Игорь Богомазов Главный технический специалист HighLink Ltd. St-Petersburg, Russia 8(812)334-12-12 [доб. 220] 8(931)238-94-41 (Мегафон) http://www.hl.ru
#include <stdlib.h>
#include <string.h>
#include <ffi.h>
#define MAX_ARGS 256
#define CHECK(x) !(x) ? abort() : 0
static size_t my_strlen(char *s)
{
return (strlen(s));
}
int main (void)
{
ffi_type *new = malloc(sizeof(ffi_type));
puts("check new");
CHECK(new);
new->size = new->alignment = 0;
new->type = FFI_TYPE_STRUCT;
new->elements = calloc(5, sizeof(ffi_type *));
puts("check new->elements");
CHECK(new->elements);
new->elements[0] = &ffi_type_uchar;
new->elements[1] = &ffi_type_uchar;
new->elements[2] = &ffi_type_uchar;
new->elements[3] = &ffi_type_uchar;
new->elements[4] = NULL;
ffi_cif cif;
ffi_type *args[MAX_ARGS];
void *values[MAX_ARGS];
ffi_arg rint;
puts("check ffi_arg");
CHECK(sizeof(ffi_arg) == 4);
char *s;
args[0] = &ffi_type_pointer;
values[0] = (void*) &s;
/* Initialize the cif */
puts("init");
CHECK(ffi_prep_cif(&cif, FFI_DEFAULT_ABI, 1,
new, args) == FFI_OK);
// &ffi_type_sint, args) == FFI_OK);
puts("size of the structure");
CHECK(new->size == 4);
// CHECK(ffi_type_sint.size == 4);
s = "a";
ffi_call(&cif, FFI_FN(my_strlen), &rint, values);
puts("check 1");
CHECK(rint == 1);
s = "1234567";
ffi_call(&cif, FFI_FN(my_strlen), &rint, values);
puts("check 7");
CHECK(rint == 7);
s = "1234567890123456789012345";
ffi_call(&cif, FFI_FN(my_strlen), &rint, values);
puts("check 25");
CHECK(rint == 25);
exit (0);
}
Attachment:
signature.asc
Description: PGP signature