[erlang-questions] Erlang FFI: 1st discussion summary
Martin Bjorklund
mbj@REDACTED
Fri Sep 14 11:29:56 CEST 2007
Hi,
Alceste Scalas <alceste@REDACTED> wrote:
> --------------------------------------------------
> 1.1. Getting information about preloaded functions
> --------------------------------------------------
>
> The proposed high-level ffi:call/3 would need information about
> functions and FFI signatures preloaded with
> erl_ddll:load_library/3. This information could be useful for
> developers, too (e.g. for debugging pourposes). For these
> reasons, the erl_ddll:info/2 BIF could be extended with a
> 'preloads' argument, that would return a list of preloaded
> functions, signatures etc. This information could be obtained
> via erl_ddll:info/1 and erl_ddll:info/0 as well.
This seems very useful.
> ======================================================
> 2. Creating Erlang binaries from C strings and buffers
> ======================================================
>
> The first proposal on this issue [5] can be revised considering type
> tagging. A new 'cstring' type atom/tag can be introduced, in order
> to distinguish NULL-terminated C strings from generic 'pointer's to
> byte buffers. Two functions could be used for turning them into
> Erlang binaries:
>
> ffi:cstring_to_binary(TaggedCString) -> binary()
> TaggedCString = {cstring, CStringPtr}
> CStringPtr = integer()
>
> Return a new binary with a copy of the given NULL-terminated
> C string (including the trailing \0);
>
> ffi:buffer_to_binary(TaggedPointer, Size) -> binary()
> TaggedPointer = {pointer, Ptr}
> Ptr = integer()
>
> Return a new binary filled with a copy of Size bytes read
> from the given C pointer.
>
> These two functions would have, as seen in the previous section,
> their type-untagged equivalents: ffi:raw_cstring_to_binary/1 and
> ffi:raw_buffer_to_binary/2.
In this case, I don't think the tagging gives you anything.
Another thing that would be nice would be to be able to get to a
ref-counted binary in the C-code; i.e. let the C-code inc the ref
count if it wants to. This would save a copy when the binary is very
big.
> ==================================
> 3. Determining the size of C types
> ==================================
>
> The sizes of C types could be determined in run-time with a new
> ffi:sizeof/1 BIF (initially proposed in [6]):
>
> * ffi:sizeof(CType) -> integer()
> CType = type_tag()
>
> Return the number of bytes used by CType on the current
> platform.
>
> Type size information should, in general, *not* be hardcoded,
> because it may change when running the same BEAM files on different
> architectures. The BIF above is the recommended way for getting
> type sizes when writing portable code.
>
> However, when the FFI-based code is *not* expected to be portable
> without recompilation, the size of C types remains constant and
> could be determined when the Erlang/OTP sources are compiled. Thus,
> this information could be stored in a .hrl file. Developers could
> -include_lib("kernel/include/ffi_hardcodes.hrl") [7] and obtain a
> set of faster and easier-to-use macros, for each supported FFI type:
>
> FFI_HARDCODED_SIZEOF_<TYPE>
> The type size in bytes
>
> FFI_HARDCODED_<TYPE>_BITS
> The type size in bits
>
> The size in bits is precomputed in order to simplify binary
> matching, since expressions like (?FFI_HARDCODED_SIZEOF_LONG * 8)
> are not allowed in patterns.
I think both these suggestions makes sense. For the use case I have
in mind (which currently is implemented as a driver), I would use the
hardcoded constants.
/martin
More information about the erlang-questions
mailing list