Jsctypes/api: Difference between revisions

Jump to navigation Jump to search
5,811 bytes added ,  24 September 2009
add jorendorff stuff, partly compatible
(add jorendorff stuff, partly compatible)
Line 1: Line 1:
== jsctypes: API for types, structs, and pointers ==
==== 1. opening a library and declaring a function ====
==== 1. opening a library and declaring a function ====
<pre>Cu.import("ctypes"); // imports the global ctypes object
<pre>Cu.import("ctypes"); // imports the global ctypes object
Line 91: Line 89:
let v = new v_t(new Pointer(s), new Pointer(s));</pre>
let v = new v_t(new Pointer(s), new Pointer(s));</pre>
In this case, the fields array will each have their respective Pointer as the parent object, and both will point to the s binary blob.<br>
In this case, the fields array will each have their respective Pointer as the parent object, and both will point to the s binary blob.<br>
----
'''js-ctypes''' is a library for calling C/C++ functions from JavaScript without having to write or generate any C/C++ "glue code".
js-ctypes is already in mozilla-central, but the API is subject to change. This page contains design proposals for the eventual js-ctypes API.
= Types =
A ''type'' maps JS values to C/C++ values and vice versa. They're used when declaring functions. They can also be used to create and populate C/C++ data structures entirely from JS.
== The types provided by ctypes ==
'''ctypes.int8_t, uint8_t, int16_t, uint16_t, int32_t, uint32_t, int64_t, uint64_t, float32_t, float64_t''' - Primitive types that behave the same way on all platforms (with the usual caveat that every platform has slightly different floating-point behavior, in corner cases, and there's nothing we can realistically do about it).
'''ctypes.bool, short, unsigned_short, int, unsigned, unsigned_int, long, unsigned_long, float, double''' - Types that behave like the corresponding C types. Some or all of these might be aliases for the primitive types listed above. As in C, ''unsigned'' is always an alias for ''unsigned_int''.
''(Note: I think <code>int</code> might be reserved in JS, sigh.)''
''(TBD: Do we want char types? how should they behave?)''
'''ctypes.string, ustring''' - String types. The C/C++ type for <code>ctypes.string</code> is <code>const char *</code>. C/C++ values of this type must be either <code>null</code> or pointers to null-terminated strings. <code>ctypes.ustring</code> is the same, but for <code>const jschar *</code>; that is, the code units of the string are <code>uint16_t</code>.
'''ctypes.void_t''' - The special C type <code>void</code>. This can be used as a return value type.  (<code>void</code> is a keyword in JavaScript.)
'''ctypes.PointerType''' - Constructor for pointer types.  ''new ctypes.PointerType(T)'', where ''T'' is a type, creates the type "pointer to ''T''".  Also ''new ctypes.PointerType(name)'', where ''name'' is a string, creates an opaque pointer type.
'''ctypes.ArrayType''' - Constructor for array types.  ''new ctypes.ArrayType(T, n)'', where ''T'' is a type and ''n'' is a nonnegative integer, creates the type ''T''[''n''].
'''ctypes.StructType''' - Constructor for struct types.  ''new ctypes.StructType(name, fields)'' creates a new struct named "struct ''name''" with the given fields (fields is an array of field descriptors), details TBD.
Examples:
  const DWORD = ctypes.uint32_t;
  const HANDLE = new ctypes.PointerType("HANDLE");
  const FILE = new ctypes.PointerType("FILE *");
  const IOBuf = new ctypes.ArrayType(ctypes.uint8_t, 4096);
  const struct_tm = new ctypes.Struct('tm', [[ctypes.int, 'tm_sec'], ...]);
== Calling types ==
js-ctypes types are JavaScript constructors. That is, they are functions, and they can be called in various different ways.  (<code>ctypes.Buffer</code> and <code>ctypes.Reference</code> are to be described below.)
'''new ''t''''' or '''new ''t''()''' - Without arguments, these allocate a new <code>ctypes.Buffer</code> of <code>''t''.size</code> bytes, populate it with zeroes, and return a new <code>ctypes.Reference</code> to the complete object in that <code>Buffer</code>.
'''''t''()''' - The same, but if the resulting value can be precisely represented as a JavaScript primitive value (boolean, number, string, null, undefined), return that instead. (This is the case for all number types, string types, pointer types, <code>ctypes.bool</code>, and <code>ctypes.void_t</code>.)
'''new ''t''(''ref'')''' - With a single argument that is a reference to an object of size <code>''t''.size</code>, this creates a new <code>Buffer</code> and <code>Reference</code> as above, but populates the buffer with a copy of the object referred to by ''ref'' rather than zeroing it out.
'''new ''t(''val'')''' - With an argument that is any other JavaScript value, this converts the value to type ''t'', throwing a <code>TypeError</code> if the conversion is impossible, then creates a new <code>Buffer</code> and <code>Reference</code> as above, populating the new buffer with the converted value.  Details of conversion depend on the type.
'''''t''(''val'')''' - Convert ''val'' to type ''t'' as above. If the result can be precisely represented as a JavaScript primitive value (boolean, number, string, <code>null</code>, or <code>undefined</code>) or a ctypes pointer, return that. Otherwise return a new Reference, exactly as for <code>new ''t''(''val'')</code>.
The special type <code>ctypes.void_t</code> throws a <code>TypeError</code> if called with <code>new</code>, but <code>ctypes.void_t()</code> and <code>ctypes.void_t(''x'')</code> are allowed. Both return <code>undefined</code>.
== Properties of types ==
All types have these properties:
'''''t''.size''' - The C/C++ <code>sizeof</code> the type, in bytes.
<code>ctypes.void_t.size</code> is 0.
'''''t''.name''' - A string, the type's name. It's intended that in ordinary use, this will be a C/C++ type expression, but it's not really meant to be machine-readable in all cases.
For primitive types this is just the name of the corresponding C/C++ type, e.g. <code>ctypes.int32_t.name == "int32_t"</code> and <code>ctypes.void_t == "void"</code>. But some of the builtin types are aliases for other types, so it might be that <code>ctypes.unsigned_long.name == "uint32_t"</code> (or something else). ''(Is that too astonishing?)''
For struct types and opaque pointer types, this is simply the string that was passed to the constructor; e.g. <code>FILE.name == "FILE *"</code> and <code>struct_tm.name == "tm"</code>. For other pointer types and array types this should try to generate valid C/C++ type expressions, which isn't exactly trivial.
''(Should you be able to assign to type.name for types you create, the effect being kind of like a typedef?)''
638

edits

Navigation menu