This is the mail archive of the
libffi-discuss@sourceware.org
mailing list for the libffi project.
Re: RFC: Delegates (or something)
On Sat, Apr 18, 2009 at 04:01:53PM -0700, William Ahern wrote:
> On Sat, Apr 18, 2009 at 03:04:33PM -0700, William Ahern wrote:
> > I'm curious of people's thoughts on this. Especially if somebody can point
> > out a bug, including the "you just got lucky that it works" kind.
> >
>
> FYI, GCC 4.2.4 on Ubuntu Hardy (host x86_64, target x86_64) returns false
> for
>
> __builtin_types_compatible_p(long long, int64_t)
>
> In fact, it seems to return false for all the stdint.h types I tried. But
> not necessarily for any typedef, since manaully defining a long long
> typedef gives the correct/expected result.
>
> A fix would be to extend the ffi_typeof and ffi_type macros, I suppose.
A fix:
--- delegate.c Sat Apr 18 14:32:42 2009
+++ delegate.c.new Sat Apr 18 16:57:37 2009
@@ -28,35 +28,78 @@
#include <stdint.h>
+#include <limits.h>
+
#include <string.h>
#include <ffi/ffi.h>
+#define ffi_bits(t) (sizeof (t) * CHAR_BIT)
+
+#define ffi_int8_compatible(t) \
+ ((__builtin_types_compatible_p(t, int8_t)) || \
+ (__builtin_types_compatible_p(t, signed char) && ffi_bits(t) == 8))
+
+#define ffi_uint8_compatible(t) \
+ ((__builtin_types_compatible_p(t, uint8_t)) || \
+ (__builtin_types_compatible_p(t, unsigned char) && ffi_bits(t) == 8))
+
+#define ffi_int16_compatible(t) \
+ ((__builtin_types_compatible_p(t, int16_t)) || \
+ (__builtin_types_compatible_p(t, signed char) && ffi_bits(t) == 16) || \
+ (__builtin_types_compatible_p(t, short) && ffi_bits(t) == 16))
+
+#define ffi_uint16_compatible(t) \
+ ((__builtin_types_compatible_p(t, uint16_t)) || \
+ (__builtin_types_compatible_p(t, unsigned char) && ffi_bits(t) == 16) || \
+ (__builtin_types_compatible_p(t, unsigned short) && ffi_bits(t) == 16))
+
+#define ffi_int32_compatible(t) \
+ ((__builtin_types_compatible_p(t, int32_t)) || \
+ (__builtin_types_compatible_p(t, int) && ffi_bits(t) == 32) || \
+ (__builtin_types_compatible_p(t, long) && ffi_bits(t) == 32))
+
+#define ffi_uint32_compatible(t) \
+ ((__builtin_types_compatible_p(t, uint32_t)) || \
+ (__builtin_types_compatible_p(t, unsigned int) && ffi_bits(t) == 32) || \
+ (__builtin_types_compatible_p(t, unsigned long) && ffi_bits(t) == 32))
+
+#define ffi_int64_compatible(t) \
+ ((__builtin_types_compatible_p(t, int64_t)) || \
+ (__builtin_types_compatible_p(t, long) && ffi_bits(t) == 64) || \
+ (__builtin_types_compatible_p(t, long long) && ffi_bits(t) == 64))
+
+#define ffi_uint64_compatible(t) \
+ ((__builtin_types_compatible_p(t, uint64_t)) || \
+ (__builtin_types_compatible_p(t, unsigned long) && ffi_bits(t) == 64) || \
+ (__builtin_types_compatible_p(t, unsigned long long) && ffi_bits(t) == 64))
+
+
#define ffi_typeof(p) __typeof__( \
__builtin_choose_expr( \
- __builtin_types_compatible_p(__typeof__(p), uint8_t), \
+ ffi_uint8_compatible(__typeof__(p)), \
(uint8_t){ 0 }, \
__builtin_choose_expr( \
- __builtin_types_compatible_p(__typeof__(p), int8_t), \
+ ffi_int8_compatible(__typeof__(p)), \
(int8_t){ 0 }, \
__builtin_choose_expr( \
- __builtin_types_compatible_p(__typeof__(p), uint16_t), \
+ ffi_uint16_compatible(__typeof__(p)), \
(uint16_t){ 0 }, \
__builtin_choose_expr( \
- __builtin_types_compatible_p(__typeof__(p), int16_t), \
+ ffi_int16_compatible(__typeof__(p)), \
(int16_t){ 0 }, \
__builtin_choose_expr( \
- __builtin_types_compatible_p(__typeof__(p), uint32_t), \
+ ffi_uint32_compatible(__typeof__(p)), \
(uint32_t){ 0 }, \
__builtin_choose_expr( \
- __builtin_types_compatible_p(__typeof__(p), int32_t), \
+ ffi_int32_compatible(__typeof__(p)), \
(int32_t){ 0 }, \
__builtin_choose_expr( \
- __builtin_types_compatible_p(__typeof__(p), uint64_t), \
+ ffi_uint64_compatible(__typeof__(p)), \
(uint64_t){ 0 }, \
__builtin_choose_expr( \
- __builtin_types_compatible_p(__typeof__(p), int64_t), \
+ ffi_int64_compatible(__typeof__(p)), \
(int64_t){ 0 }, \
__builtin_choose_expr( \
__builtin_types_compatible_p(__typeof__(p), float), \