summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKaz Kylheku <kaz@kylheku.com>2017-05-21 15:36:06 -0700
committerKaz Kylheku <kaz@kylheku.com>2017-05-21 15:36:06 -0700
commitb580e0f60eab4b23e782b0f2970823a51e5000bd (patch)
tree80511cf9d648084fb467aa9224421c90fb476558
parent53fd7bd43eb9a513f5a81f9ebbd99a7cc4172430 (diff)
downloadtxr-b580e0f60eab4b23e782b0f2970823a51e5000bd.tar.gz
txr-b580e0f60eab4b23e782b0f2970823a51e5000bd.tar.bz2
txr-b580e0f60eab4b23e782b0f2970823a51e5000bd.zip
ffi: bugfix: revisit alignment.
Replace the incorrect alignment assumption for the basic types (size == alignment) with the true calculation obtained from the compiler. * ffi.c (alignof): New macro. (make_ffi_type_builtin): Take alignment as separate argument. (ffi_type_compile, ffi_init_types): Using alignof macro, calculate alignment of each type that is created using make_ffi_type_builtin, and pass to that function.
-rw-r--r--ffi.c92
1 files changed, 62 insertions, 30 deletions
diff --git a/ffi.c b/ffi.c
index 226e1063..bf4c401b 100644
--- a/ffi.c
+++ b/ffi.c
@@ -60,6 +60,8 @@
#define zalloca(size) memset(alloca(size), 0, size)
+#define alignof(type) offsetof(struct {char x; type y;}, y)
+
val uint8_s, int8_s;
val uint16_s, int16_s;
val uint32_s, int32_s;
@@ -1427,7 +1429,7 @@ static void ffi_carray_put(struct txr_ffi_type *tft, val carray, mem_t *dst,
}
static val make_ffi_type_builtin(val syntax, val lisp_type,
- cnum size, ffi_type *ft,
+ cnum size, cnum align, ffi_type *ft,
void (*put)(struct txr_ffi_type *,
val obj, mem_t *dst, val self),
val (*get)(struct txr_ffi_type *,
@@ -1442,7 +1444,8 @@ static val make_ffi_type_builtin(val syntax, val lisp_type,
tft->syntax = syntax;
tft->lt = lisp_type;
tft->mnames = tft->mtypes = nil;
- tft->size = tft->align = size;
+ tft->size = size;
+ tft->align = align;
tft->put = put;
tft->get = get;
tft->alloc = ffi_fixed_alloc;
@@ -1746,6 +1749,7 @@ val ffi_type_compile(val syntax)
cnum nelem = c_num(cadr(syntax));
val type = make_ffi_type_builtin(syntax, buf_s,
sizeof (mem_t *),
+ alignof (mem_t *),
&ffi_type_pointer,
if3(sym == buf_s,
ffi_buf_put, ffi_buf_d_put),
@@ -1769,6 +1773,7 @@ val ffi_type_compile(val syntax)
} else if (sym == cptr_s) {
val tag = cadr(syntax);
val type = make_ffi_type_builtin(syntax, cptr_s, sizeof (mem_t *),
+ alignof (mem_t *),
&ffi_type_pointer,
ffi_cptr_put, ffi_cptr_get);
struct txr_ffi_type *tft = ffi_type_struct(type);
@@ -1777,6 +1782,7 @@ val ffi_type_compile(val syntax)
} else if (sym == carray_s) {
val element_type = ffi_type_compile(cadr(syntax));
val type = make_ffi_type_builtin(syntax, carray_s, sizeof (mem_t *),
+ alignof (mem_t *),
&ffi_type_pointer,
ffi_carray_put, ffi_carray_get);
struct txr_ffi_type *tft = ffi_type_struct(type);
@@ -1806,75 +1812,92 @@ static void ffi_init_types(void)
#if HAVE_I8
ffi_typedef(uint8_s, make_ffi_type_builtin(uint8_s, integer_s, sizeof (i8_t),
- &ffi_type_uint8,
+ alignof (i8_t), &ffi_type_uint8,
ffi_u8_put, ffi_u8_get));
ffi_typedef(int8_s, make_ffi_type_builtin(int8_s, integer_s, sizeof (i8_t),
- &ffi_type_sint8,
+ alignof (i8_t), &ffi_type_sint8,
ffi_i8_put, ffi_i8_get));
#endif
#if HAVE_I16
ffi_typedef(uint16_s, make_ffi_type_builtin(uint16_s, integer_s,
- sizeof (i16_t),
+ sizeof (i16_t), alignof (i16_t),
&ffi_type_uint16,
ffi_u16_put, ffi_u16_get));
ffi_typedef(int16_s, make_ffi_type_builtin(int16_s, integer_s,
- sizeof (i16_t),
+ sizeof (i16_t), alignof (i16_t),
&ffi_type_sint16,
ffi_i16_put, ffi_i16_get));
#endif
#if HAVE_I32
ffi_typedef(uint32_s, make_ffi_type_builtin(uint32_s, integer_s,
- sizeof (i32_t), &ffi_type_uint32,
+ sizeof (i32_t), alignof (i32_t),
+ &ffi_type_uint32,
ffi_u32_put, ffi_u32_get));
ffi_typedef(int32_s, make_ffi_type_builtin(int32_s, integer_s,
- sizeof (i32_t), &ffi_type_sint32,
+ sizeof (i32_t), alignof (i32_t),
+ &ffi_type_sint32,
ffi_i32_put, ffi_i32_get));
#endif
#if HAVE_I64
ffi_typedef(uint64_s, make_ffi_type_builtin(uint64_s, integer_s,
- sizeof (i64_t), &ffi_type_uint64,
+ sizeof (i64_t), alignof (i64_t),
+ &ffi_type_uint64,
ffi_u64_put, ffi_u64_get));
ffi_typedef(int64_s, make_ffi_type_builtin(int64_s, integer_s,
- sizeof (i64_t), &ffi_type_sint64,
+ sizeof (i64_t), alignof (i64_t),
+ &ffi_type_sint64,
ffi_i64_put, ffi_i64_get));
#endif
- ffi_typedef(uchar_s, make_ffi_type_builtin(uchar_s, integer_s, 1, &ffi_type_uchar,
+ ffi_typedef(uchar_s, make_ffi_type_builtin(uchar_s, integer_s, 1, 1,
+ &ffi_type_uchar,
ffi_uchar_put, ffi_uchar_get));
- ffi_typedef(char_s, make_ffi_type_builtin(char_s, integer_s, 1,
+ ffi_typedef(char_s, make_ffi_type_builtin(char_s, integer_s, 1, 1,
ffi_char, ffi_char_put, ffi_char_get));
- ffi_typedef(bchar_s, make_ffi_type_builtin(bchar_s, char_s,
- sizeof (char), &ffi_type_uchar,
+ ffi_typedef(bchar_s, make_ffi_type_builtin(bchar_s, char_s, 1, 1,
+ &ffi_type_uchar,
ffi_uchar_put, ffi_bchar_get));
ffi_typedef(wchar_s, make_ffi_type_builtin(wchar_s, char_s,
- sizeof (wchar_t), &ffi_type_wchar,
+ sizeof (wchar_t),
+ alignof (wchar_t),
+ &ffi_type_wchar,
ffi_wchar_put, ffi_wchar_get));
ffi_typedef(ushort_s, make_ffi_type_builtin(ushort_s, integer_s,
- sizeof (short), &ffi_type_ushort,
+ sizeof (short), alignof (short),
+ &ffi_type_ushort,
ffi_ushort_put, ffi_ushort_get));
ffi_typedef(short_s, make_ffi_type_builtin(short_s, integer_s,
- sizeof (short), &ffi_type_sshort,
+ sizeof (short), alignof (short),
+ &ffi_type_sshort,
ffi_short_put, ffi_short_get));
ffi_typedef(int_s, make_ffi_type_builtin(int_s, integer_s,
- sizeof (int), &ffi_type_sint,
+ sizeof (int), alignof (int),
+ &ffi_type_sint,
ffi_int_put, ffi_int_get));
ffi_typedef(uint_s, make_ffi_type_builtin(uint_s, integer_s,
- sizeof (int), &ffi_type_uint,
+ sizeof (int), alignof (int),
+ &ffi_type_uint,
ffi_uint_put, ffi_uint_get));
ffi_typedef(ulong_s, make_ffi_type_builtin(ulong_s, integer_s,
- sizeof (long), &ffi_type_ulong,
+ sizeof (long), alignof (long),
+ &ffi_type_ulong,
ffi_ulong_put, ffi_ulong_get));
ffi_typedef(long_s, make_ffi_type_builtin(long_s, integer_s,
- sizeof (long), &ffi_type_slong,
+ sizeof (long), alignof (long),
+ &ffi_type_slong,
ffi_long_put, ffi_long_get));
ffi_typedef(float_s, make_ffi_type_builtin(float_s, float_s,
- sizeof (float), &ffi_type_float,
+ sizeof (float), alignof (float),
+ &ffi_type_float,
ffi_float_put, ffi_float_get));
ffi_typedef(double_s, make_ffi_type_builtin(double_s, float_s,
- sizeof (double), &ffi_type_double,
+ sizeof (double),
+ alignof (double),
+ &ffi_type_double,
ffi_double_put, ffi_double_get));
{
val type = make_ffi_type_builtin(cptr_s, cptr_s, sizeof (mem_t *),
+ alignof (mem_t *),
&ffi_type_pointer,
ffi_cptr_put, ffi_cptr_get);
struct txr_ffi_type *tft = ffi_type_struct(type);
@@ -1885,6 +1908,7 @@ static void ffi_init_types(void)
{
val type = make_ffi_type_builtin(str_s, str_s, sizeof (mem_t *),
+ alignof (mem_t *),
&ffi_type_pointer,
ffi_str_put, ffi_str_get);
struct txr_ffi_type *tft = ffi_type_struct(type);
@@ -1895,6 +1919,7 @@ static void ffi_init_types(void)
{
val type = make_ffi_type_builtin(bstr_s, str_s, sizeof (mem_t *),
+ alignof (mem_t *),
&ffi_type_pointer,
ffi_bstr_put, ffi_bstr_get);
struct txr_ffi_type *tft = ffi_type_struct(type);
@@ -1903,12 +1928,14 @@ static void ffi_init_types(void)
ffi_typedef(bstr_s, type);
}
- ffi_typedef(str_d_s, make_ffi_type_builtin(str_d_s, str_s,
- sizeof (mem_t *), &ffi_type_pointer,
+ ffi_typedef(str_d_s, make_ffi_type_builtin(str_d_s, str_s, sizeof (mem_t *),
+ alignof (mem_t *),
+ &ffi_type_pointer,
ffi_str_put, ffi_str_d_get));
{
val type = ffi_typedef(wstr_s, make_ffi_type_builtin(wstr_s, str_s,
sizeof (mem_t *),
+ alignof (mem_t *),
&ffi_type_pointer,
ffi_wstr_put,
ffi_wstr_get));
@@ -1918,11 +1945,13 @@ static void ffi_init_types(void)
ffi_typedef(wstr_s, type);
}
- ffi_typedef(wstr_d_s, make_ffi_type_builtin(wstr_d_s, str_s,
- sizeof (mem_t *), &ffi_type_pointer,
+ ffi_typedef(wstr_d_s, make_ffi_type_builtin(wstr_d_s, str_s, sizeof (mem_t *),
+ alignof (mem_t *),
+ &ffi_type_pointer,
ffi_wstr_put, ffi_wstr_d_get));
- ffi_typedef(bstr_d_s, make_ffi_type_builtin(bstr_d_s, str_s,
- sizeof (mem_t *), &ffi_type_pointer,
+ ffi_typedef(bstr_d_s, make_ffi_type_builtin(bstr_d_s, str_s, sizeof (mem_t *),
+ alignof (mem_t *),
+ &ffi_type_pointer,
ffi_bstr_put, ffi_bstr_d_get));
{
@@ -1931,6 +1960,7 @@ static void ffi_init_types(void)
for (iter = list(buf_s, buf_d_s, nao); iter; iter = cdr(iter)) {
val sym = car(iter);
ffi_typedef(sym, make_ffi_type_builtin(sym, buf_s, sizeof (mem_t *),
+ alignof (mem_t *),
&ffi_type_pointer,
if3(sym == buf_s,
ffi_buf_put, ffi_buf_d_put),
@@ -1940,9 +1970,11 @@ static void ffi_init_types(void)
ffi_typedef(closure_s, make_ffi_type_builtin(closure_s, fun_s,
sizeof (mem_t *),
+ alignof (mem_t *),
&ffi_type_pointer,
ffi_closure_put, ffi_cptr_get));
- ffi_typedef(void_s, make_ffi_type_builtin(void_s, null_s, 0, &ffi_type_void,
+ ffi_typedef(void_s, make_ffi_type_builtin(void_s, null_s, 0, 0,
+ &ffi_type_void,
ffi_void_put, ffi_void_get));
}