From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 11737 invoked by alias); 31 Oct 2014 17:28:05 -0000 Mailing-List: contact jit-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Post: List-Help: List-Subscribe: Sender: jit-owner@gcc.gnu.org Received: (qmail 11721 invoked by uid 89); 31 Oct 2014 17:28:04 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Checked: by ClamAV 0.98.4 on sourceware.org X-Virus-Found: No X-Spam-SWARE-Status: No, score=-0.7 required=5.0 tests=AWL,BAYES_50 autolearn=ham version=3.3.2 X-Spam-Status: No, score=-0.7 required=5.0 tests=AWL,BAYES_50 autolearn=ham version=3.3.2 X-Spam-Checker-Version: SpamAssassin 3.3.2 (2011-06-06) on sourceware.org X-Spam-Level: X-HELO: eggs.gnu.org From: David Malcolm To: gcc-patches@gcc.gnu.org, jit@gcc.gnu.org Cc: David Malcolm Subject: [PATCH 24/27] Documentation: add "topics" subdirectory Date: Wed, 01 Jan 2014 00:00:00 -0000 Message-Id: <1414774977-25605-24-git-send-email-dmalcolm@redhat.com> In-Reply-To: <1414774977-25605-1-git-send-email-dmalcolm@redhat.com> References: <1414774977-25605-1-git-send-email-dmalcolm@redhat.com> X-Scanned-By: MIMEDefang 2.68 on 10.5.11.24 X-detected-operating-system: by eggs.gnu.org: GNU/Linux 3.x X-Received-From: 209.132.183.28 X-SW-Source: 2014-q4/txt/msg00076.txt.bz2 This patch adds a series of topic-based reference articles, intended to give developers who've read the tutorial more detailed descriptions of particular aspects of the library. gcc/jit/ * docs/topics/contexts.rst: New. * docs/topics/expressions.rst: New. * docs/topics/functions.rst: New. * docs/topics/index.rst: New. * docs/topics/locations.rst: New. * docs/topics/objects.rst: New. * docs/topics/results.rst: New. * docs/topics/types.rst: New. --- gcc/jit/docs/topics/contexts.rst | 315 ++++++++++++++++++++++ gcc/jit/docs/topics/expressions.rst | 524 ++++++++++++++++++++++++++++++++++++ gcc/jit/docs/topics/functions.rst | 311 +++++++++++++++++++++ gcc/jit/docs/topics/index.rst | 30 +++ gcc/jit/docs/topics/locations.rst | 69 +++++ gcc/jit/docs/topics/objects.rst | 86 ++++++ gcc/jit/docs/topics/results.rst | 48 ++++ gcc/jit/docs/topics/types.rst | 217 +++++++++++++++ 8 files changed, 1600 insertions(+) create mode 100644 gcc/jit/docs/topics/contexts.rst create mode 100644 gcc/jit/docs/topics/expressions.rst create mode 100644 gcc/jit/docs/topics/functions.rst create mode 100644 gcc/jit/docs/topics/index.rst create mode 100644 gcc/jit/docs/topics/locations.rst create mode 100644 gcc/jit/docs/topics/objects.rst create mode 100644 gcc/jit/docs/topics/results.rst create mode 100644 gcc/jit/docs/topics/types.rst diff --git a/gcc/jit/docs/topics/contexts.rst b/gcc/jit/docs/topics/contexts.rst new file mode 100644 index 0000000..d8dd4f8 --- /dev/null +++ b/gcc/jit/docs/topics/contexts.rst @@ -0,0 +1,315 @@ +.. Copyright (C) 2014 Free Software Foundation, Inc. + Originally contributed by David Malcolm + + This is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see + . + +.. default-domain:: c + +Compilation contexts +==================== + +.. type:: gcc_jit_context + +The top-level of the API is the :c:type:`gcc_jit_context` type. + +A :c:type:`gcc_jit_context` instance encapsulates the state of a +compilation. + +You can set up options on it, and add types, functions and code. +Invoking :c:func:`gcc_jit_context_compile` on it gives you a +:c:type:`gcc_jit_result`. + +Lifetime-management +------------------- +Contexts are the unit of lifetime-management within the API: objects +have their lifetime bounded by the context they are created within, and +cleanup of such objects is done for you when the context is released. + +.. function:: gcc_jit_context *gcc_jit_context_acquire (void) + + This function acquires a new :c:type:`gcc_jit_object *` instance, + which is independent of any others that may be present within this + process. + +.. function:: void gcc_jit_context_release (gcc_jit_context *ctxt) + + This function releases all resources associated with the given context. + Both the context itself and all of its :c:type:`gcc_jit_object *` + instances are cleaned up. It should be called exactly once on a given + context. + + It is invalid to use the context or any of its "contextual" objects + after calling this. + + .. code-block:: c + + gcc_jit_context_release (ctxt); + +.. function:: gcc_jit_context * gcc_jit_context_new_child_context (gcc_jit_context *parent_ctxt) + + Given an existing JIT context, create a child context. + + The child inherits a copy of all option-settings from the parent. + + The child can reference objects created within the parent, but not + vice-versa. + + The lifetime of the child context must be bounded by that of the + parent: you should release a child context before releasing the parent + context. + + If you use a function from a parent context within a child context, + you have to compile the parent context before you can compile the + child context, and the gcc_jit_result of the parent context must + outlive the gcc_jit_result of the child context. + + This allows caching of shared initializations. For example, you could + create types and declarations of global functions in a parent context + once within a process, and then create child contexts whenever a + function or loop becomes hot. Each such child context can be used for + JIT-compiling just one function or loop, but can reference types + and helper functions created within the parent context. + + Contexts can be arbitrarily nested, provided the above rules are + followed, but it's probably not worth going above 2 or 3 levels, and + there will likely be a performance hit for such nesting. + + +Thread-safety +------------- +Instances of :c:type:`gcc_jit_object *` created via +:c:func:`gcc_jit_context_acquire` are independent from each other: +only one thread may use a given context at once, but multiple threads +could each have their own contexts without needing locks. + +Contexts created via :c:func:`gcc_jit_context_new_child_context` are +related to their parent context. They can be partitioned by their +ultimate ancestor into independent "family trees". Only one thread +within a process may use a given "family tree" of such contexts at once, +and if you're using multiple threads you should provide your own locking +around entire such context partitions. + + +Error-handling +-------------- +You can only compile and get code from a context if no errors occur. + +In general, if an error occurs when using an API entrypoint, it returns +NULL. You don't have to check everywhere for NULL results, since the +API gracefully handles a NULL being passed in for any argument. + +Errors are printed on stderr and can be queried using +:c:func:`gcc_jit_context_get_first_error`. + +.. function:: const char *\ + gcc_jit_context_get_first_error (gcc_jit_context *ctxt) + + Returns the first error message that occurred on the context. + + The returned string is valid for the rest of the lifetime of the + context. + + If no errors occurred, this will be NULL. + +Debugging +--------- + +.. function:: void\ + gcc_jit_context_dump_to_file (gcc_jit_context *ctxt,\ + const char *path,\ + int update_locations) + + To help with debugging: dump a C-like representation to the given path, + describing what's been set up on the context. + + If "update_locations" is true, then also set up :type:`gcc_jit_location` + information throughout the context, pointing at the dump file as if it + were a source file. This may be of use in conjunction with + :macro:`GCC_JIT_BOOL_OPTION_DEBUGINFO` to allow stepping through the + code in a debugger. + + +Options +------- + +String Options +************** + +.. function:: void gcc_jit_context_set_str_option(gcc_jit_context *ctxt, \ + enum gcc_jit_str_option opt, \ + const char *value) + + Set a string option of the context. + + .. type:: enum gcc_jit_str_option + + There is currently just one string option: + + .. macro:: GCC_JIT_STR_OPTION_PROGNAME + + The name of the program, for use as a prefix when printing error + messages to stderr. If `NULL`, or default, "libgccjit.so" is used. + +Boolean options +*************** + +.. function:: void gcc_jit_context_set_bool_option(gcc_jit_context *ctxt, \ + enum gcc_jit_bool_option opt, \ + int value) + + Set a boolean option of the context. + Zero is "false" (the default), non-zero is "true". + + .. type:: enum gcc_jit_bool_option + + .. macro:: GCC_JIT_BOOL_OPTION_DEBUGINFO + + If true, :func:`gcc_jit_context_compile` will attempt to do the right + thing so that if you attach a debugger to the process, it will + be able to inspect variables and step through your code. + + Note that you can't step through code unless you set up source + location information for the code (by creating and passing in + :type:`gcc_jit_location` instances). + + .. macro:: GCC_JIT_BOOL_OPTION_DUMP_INITIAL_TREE + + If true, :func:`gcc_jit_context_compile` will dump its initial + "tree" representation of your code to stderr (before any + optimizations). + + Here's some sample output (from the `square` example):: + + > + side-effects head 0x7f4875a761e0 tail 0x7f4875a761f8 stmts 0x7f4875a62d20 0x7f4875a62d00 + + stmt + side-effects + arg 0 + VOID file (null) line 0 col 0 + align 1 context >> + stmt + unit size + align 32 symtab 0 alias set -1 canonical type 0x7f4875a645e8 precision 32 min max + pointer_to_this > + side-effects + arg 0 + side-effects arg 0 + arg 1 + arg 0 arg 1 >>>> + + .. macro:: GCC_JIT_BOOL_OPTION_DUMP_INITIAL_GIMPLE + + If true, :func:`gcc_jit_context_compile` will dump the "gimple" + representation of your code to stderr, before any optimizations + are performed. The dump resembles C code: + + .. code-block:: c + + square (signed int i) + { + signed int D.56; + + entry: + D.56 = i * i; + return D.56; + } + + .. macro:: GCC_JIT_BOOL_OPTION_DUMP_GENERATED_CODE + + If true, :func:`gcc_jit_context_compile` will dump the final + generated code to stderr, in the form of assembly language: + + .. code-block:: gas + + .file "fake.c" + .text + .globl square + .type square, @function + square: + .LFB0: + .cfi_startproc + pushq %rbp + .cfi_def_cfa_offset 16 + .cfi_offset 6, -16 + movq %rsp, %rbp + .cfi_def_cfa_register 6 + movl %edi, -4(%rbp) + .L2: + movl -4(%rbp), %eax + imull -4(%rbp), %eax + popq %rbp + .cfi_def_cfa 7, 8 + ret + .cfi_endproc + .LFE0: + .size square, .-square + .ident "GCC: (GNU) 4.9.0 20131023 (Red Hat 0.1-%{gcc_release})" + .section .note.GNU-stack,"",@progbits + + + .. macro:: GCC_JIT_BOOL_OPTION_DUMP_SUMMARY + + If true, :func:`gcc_jit_context_compile` will print information to stderr + on the actions it is performing, followed by a profile showing + the time taken and memory usage of each phase. + + .. macro:: GCC_JIT_BOOL_OPTION_DUMP_EVERYTHING + + If true, :func:`gcc_jit_context_compile` will dump copious + amount of information on what it's doing to various + files within a temporary directory. Use + :macro:`GCC_JIT_BOOL_OPTION_KEEP_INTERMEDIATES` (see below) to + see the results. The files are intended to be human-readable, + but the exact files and their formats are subject to change. + + .. macro:: GCC_JIT_BOOL_OPTION_SELFCHECK_GC + + If true, libgccjit will aggressively run its garbage collector, to + shake out bugs (greatly slowing down the compile). This is likely + to only be of interest to developers *of* the library. It is + used when running the selftest suite. + + .. macro:: GCC_JIT_BOOL_OPTION_KEEP_INTERMEDIATES + + If true, the :type:`gcc_jit_context` will not clean up intermediate files + written to the filesystem, and will display their location on stderr. + +Integer options +*************** + +.. function:: void gcc_jit_context_set_int_option (gcc_jit_context *ctxt, \ + enum gcc_jit_int_option opt, \ + int value) + + Set an integer option of the context. + + .. type:: enum gcc_jit_int_option + + There is currently just one integer option: + + .. macro:: GCC_JIT_INT_OPTION_OPTIMIZATION_LEVEL + + How much to optimize the code. + + Valid values are 0-3, corresponding to GCC's command-line options + -O0 through -O3. + + The default value is 0 (unoptimized). diff --git a/gcc/jit/docs/topics/expressions.rst b/gcc/jit/docs/topics/expressions.rst new file mode 100644 index 0000000..a95f5c9 --- /dev/null +++ b/gcc/jit/docs/topics/expressions.rst @@ -0,0 +1,524 @@ +.. Copyright (C) 2014 Free Software Foundation, Inc. + Originally contributed by David Malcolm + + This is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see + . + +.. default-domain:: c + +Expressions +=========== + +Rvalues +------- +.. type:: gcc_jit_rvalue + +A :c:type:`gcc_jit_rvalue *` is an expression that can be computed. + +It can be simple, e.g.: + + * an integer value e.g. `0` or `42` + * a string literal e.g. `"Hello world"` + * a variable e.g. `i`. These are also lvalues (see below). + +or compound e.g.: + + * a unary expression e.g. `!cond` + * a binary expression e.g. `(a + b)` + * a function call e.g. `get_distance (&player_ship, &target)` + * etc. + +Every rvalue has an associated type, and the API will check to ensure +that types match up correctly (otherwise the context will emit an error). + +.. function:: gcc_jit_type *gcc_jit_rvalue_get_type (gcc_jit_rvalue *rvalue) + + Get the type of this rvalue. + +.. function:: gcc_jit_object *gcc_jit_rvalue_as_object (gcc_jit_rvalue *rvalue) + + Upcast the given rvalue to be an object. + + +Simple expressions +****************** + +.. function:: gcc_jit_rvalue *\ + gcc_jit_context_new_rvalue_from_int (gcc_jit_context *ctxt, \ + gcc_jit_type *numeric_type, \ + int value) + + Given a numeric type (integer or floating point), build an rvalue for + the given constant value. + +.. function:: gcc_jit_rvalue *gcc_jit_context_zero (gcc_jit_context *ctxt, \ + gcc_jit_type *numeric_type) + + Given a numeric type (integer or floating point), get the rvalue for + zero. Essentially this is just a shortcut for: + + .. code-block:: c + + gcc_jit_context_new_rvalue_from_int (ctxt, numeric_type, 0) + +.. function:: gcc_jit_rvalue *gcc_jit_context_one (gcc_jit_context *ctxt, \ + gcc_jit_type *numeric_type) + + Given a numeric type (integer or floating point), get the rvalue for + zero. Essentially this is just a shortcut for: + + .. code-block:: c + + gcc_jit_context_new_rvalue_from_int (ctxt, numeric_type, 1) + +.. function:: gcc_jit_rvalue *\ + gcc_jit_context_new_rvalue_from_double (gcc_jit_context *ctxt, \ + gcc_jit_type *numeric_type, \ + double value) + + Given a numeric type (integer or floating point), build an rvalue for + the given constant value. + +.. function:: gcc_jit_rvalue *\ + gcc_jit_context_new_rvalue_from_ptr (gcc_jit_context *ctxt, \ + gcc_jit_type *pointer_type, \ + void *value) + + Given a pointer type, build an rvalue for the given address. + +.. function:: gcc_jit_rvalue *gcc_jit_context_null (gcc_jit_context *ctxt, \ + gcc_jit_type *pointer_type) + + Given a pointer type, build an rvalue for ``NULL``. Essentially this + is just a shortcut for: + + .. code-block:: c + + gcc_jit_context_new_rvalue_from_ptr (ctxt, pointer_type, NULL) + +.. function:: gcc_jit_rvalue *\ + gcc_jit_context_new_string_literal (gcc_jit_context *ctxt, \ + const char *value) + + Generate an rvalue for the given NIL-terminated string, of type + :c:data:`GCC_JIT_TYPE_CONST_CHAR_PTR`. + + +Unary Operations +**************** + +.. function:: gcc_jit_rvalue * \ + gcc_jit_context_new_unary_op (gcc_jit_context *ctxt, \ + gcc_jit_location *loc, \ + enum gcc_jit_unary_op op, \ + gcc_jit_type *result_type, \ + gcc_jit_rvalue *rvalue) + + Build a unary operation out of an input rvalue. + +.. type:: enum gcc_jit_unary_op + +The available unary operations are: + +========================================== ============ +Unary Operation C equivalent +========================================== ============ +:c:macro:`GCC_JIT_UNARY_OP_MINUS` `-(EXPR)` +:c:macro:`GCC_JIT_UNARY_OP_BITWISE_NEGATE` `~(EXPR)` +:c:macro:`GCC_JIT_UNARY_OP_LOGICAL_NEGATE` `!(EXPR)` +========================================== ============ + +.. c:macro:: GCC_JIT_UNARY_OP_MINUS + + Negate an arithmetic value; analogous to: + + .. code-block:: c + + -(EXPR) + + in C. + +.. c:macro:: GCC_JIT_UNARY_OP_BITWISE_NEGATE + + Bitwise negation of an integer value (one's complement); analogous + to: + + .. code-block:: c + + ~(EXPR) + + in C. + +.. c:macro:: GCC_JIT_UNARY_OP_LOGICAL_NEGATE + + Logical negation of an arithmetic or pointer value; analogous to: + + .. code-block:: c + + !(EXPR) + + in C. + +Binary Operations +***************** + +.. function:: gcc_jit_rvalue *gcc_jit_context_new_binary_op (gcc_jit_context *ctxt, \ + gcc_jit_location *loc, \ + enum gcc_jit_binary_op op, \ + gcc_jit_type *result_type, \ + gcc_jit_rvalue *a, gcc_jit_rvalue *b) + + Build a binary operation out of two constituent rvalues. + +.. type:: enum gcc_jit_binary_op + +The available binary operations are: + +======================================== ============ +Binary Operation C equivalent +======================================== ============ +:c:macro:`GCC_JIT_BINARY_OP_PLUS` `x + y` +:c:macro:`GCC_JIT_BINARY_OP_MINUS` `x - y` +:c:macro:`GCC_JIT_BINARY_OP_MULT` `x * y` +:c:macro:`GCC_JIT_BINARY_OP_DIVIDE` `x / y` +:c:macro:`GCC_JIT_BINARY_OP_MODULO` `x % y` +:c:macro:`GCC_JIT_BINARY_OP_BITWISE_AND` `x & y` +:c:macro:`GCC_JIT_BINARY_OP_BITWISE_XOR` `x ^ y` +:c:macro:`GCC_JIT_BINARY_OP_BITWISE_OR` `x | y` +:c:macro:`GCC_JIT_BINARY_OP_LOGICAL_AND` `x && y` +:c:macro:`GCC_JIT_BINARY_OP_LOGICAL_OR` `x || y` +:c:macro:`GCC_JIT_BINARY_OP_LSHIFT` `x << y` +:c:macro:`GCC_JIT_BINARY_OP_RSHIFT` `x >> y` +======================================== ============ + +.. c:macro:: GCC_JIT_BINARY_OP_PLUS + + Addition of arithmetic values; analogous to: + + .. code-block:: c + + (EXPR_A) + (EXPR_B) + + in C. + + For pointer addition, use :c:func:`gcc_jit_context_new_array_access`. + +.. c:macro:: GCC_JIT_BINARY_OP_MINUS` + + Subtraction of arithmetic values; analogous to: + + .. code-block:: c + + (EXPR_A) - (EXPR_B) + + in C. + +.. c:macro:: GCC_JIT_BINARY_OP_MULT + + Multiplication of a pair of arithmetic values; analogous to: + + .. code-block:: c + + (EXPR_A) * (EXPR_B) + + in C. + +.. c:macro:: GCC_JIT_BINARY_OP_DIVIDE + + Quotient of division of arithmetic values; analogous to: + + .. code-block:: c + + (EXPR_A) / (EXPR_B) + + in C. + + The result type affects the kind of division: if the result type is + integer-based, then the result is truncated towards zero, whereas + a floating-point result type indicates floating-point division. + +.. c:macro:: GCC_JIT_BINARY_OP_MODULO + + Remainder of division of arithmetic values; analogous to: + + .. code-block:: c + + (EXPR_A) % (EXPR_B) + + in C. + +.. c:macro:: GCC_JIT_BINARY_OP_BITWISE_AND + + Bitwise AND; analogous to: + + .. code-block:: c + + (EXPR_A) & (EXPR_B) + + in C. + +.. c:macro:: GCC_JIT_BINARY_OP_BITWISE_XOR + + Bitwise exclusive OR; analogous to: + + .. code-block:: c + + (EXPR_A) ^ (EXPR_B) + + in C. + +.. c:macro:: GCC_JIT_BINARY_OP_BITWISE_OR + + Bitwise inclusive OR; analogous to: + + .. code-block:: c + + (EXPR_A) | (EXPR_B) + + in C. + +.. c:macro:: GCC_JIT_BINARY_OP_LOGICAL_AND + + Logical AND; analogous to: + + .. code-block:: c + + (EXPR_A) && (EXPR_B) + + in C. + +.. c:macro:: GCC_JIT_BINARY_OP_LOGICAL_OR + + Logical OR; analogous to: + + .. code-block:: c + + (EXPR_A) || (EXPR_B) + + in C. + +.. c:macro:: GCC_JIT_BINARY_OP_LSHIFT + + Left shift; analogous to: + + .. code-block:: c + + (EXPR_A) << (EXPR_B) + + in C. + +.. c:macro:: GCC_JIT_BINARY_OP_RSHIFT + + Right shift; analogous to: + + .. code-block:: c + + (EXPR_A) >> (EXPR_B) + + in C. + +Comparisons +*********** + +.. function:: gcc_jit_rvalue *\ + gcc_jit_context_new_comparison (gcc_jit_context *ctxt,\ + gcc_jit_location *loc,\ + enum gcc_jit_comparison op,\ + gcc_jit_rvalue *a, gcc_jit_rvalue *b) + + Build a boolean rvalue out of the comparison of two other rvalues. + +.. type:: enum gcc_jit_comparison + +======================================= ============ +Comparison C equivalent +======================================= ============ +:c:macro:`GCC_JIT_COMPARISON_EQ` `x == y` +:c:macro:`GCC_JIT_COMPARISON_NE` `x != y` +:c:macro:`GCC_JIT_COMPARISON_LT` `x < y` +:c:macro:`GCC_JIT_COMPARISON_LE` `x <= y` +:c:macro:`GCC_JIT_COMPARISON_GT` `x > y` +:c:macro:`GCC_JIT_COMPARISON_GE` `x >= y` +======================================= ============ + + +Function calls +************** +.. function:: gcc_jit_rvalue *\ + gcc_jit_context_new_call (gcc_jit_context *ctxt,\ + gcc_jit_location *loc,\ + gcc_jit_function *func,\ + int numargs , gcc_jit_rvalue **args) + + Given a function and the given table of argument rvalues, construct a + call to the function, with the result as an rvalue. + + .. note:: + + :c:func:`gcc_jit_context_new_call` merely builds a + :c:type:`gcc_jit_rvalue` i.e. an expression that can be evaluated, + perhaps as part of a more complicated expression. + The call *won't* happen unless you add a statement to a function + that evaluates the expression. + + For example, if you want to call a function and discard the result + (or to call a function with ``void`` return type), use + :c:func:`gcc_jit_block_add_eval`: + + .. code-block:: c + + /* Add "(void)printf (arg0, arg1);". */ + gcc_jit_block_add_eval ( + block, NULL, + gcc_jit_context_new_call ( + ctxt, + NULL, + printf_func, + 2, args)); + +Type-coercion +************* + +.. function:: gcc_jit_rvalue *\ + gcc_jit_context_new_cast (gcc_jit_context *ctxt,\ + gcc_jit_location *loc,\ + gcc_jit_rvalue *rvalue,\ + gcc_jit_type *type) + + Given an rvalue of T, construct another rvalue of another type. + + Currently only a limited set of conversions are possible: + + * int <-> float + * int <-> bool + +Lvalues +------- + +.. type:: gcc_jit_lvalue + +An lvalue is something that can of the *left*-hand side of an assignment: +a storage area (such as a variable). It is also usable as an rvalue, +where the rvalue is computed by reading from the storage area. + +.. function:: gcc_jit_object *\ + gcc_jit_lvalue_as_object (gcc_jit_lvalue *lvalue) + + Upcast an lvalue to be an object. + +.. function:: gcc_jit_rvalue *\ + gcc_jit_lvalue_as_rvalue (gcc_jit_lvalue *lvalue) + + Upcast an lvalue to be an rvalue. + +.. function:: gcc_jit_rvalue *\ + gcc_jit_lvalue_get_address (gcc_jit_lvalue *lvalue,\ + gcc_jit_location *loc) + + Take the address of an lvalue; analogous to: + + .. code-block:: c + + &(EXPR) + + in C. + +Global variables +**************** + +.. function:: gcc_jit_lvalue *\ + gcc_jit_context_new_global (gcc_jit_context *ctxt,\ + gcc_jit_location *loc,\ + gcc_jit_type *type,\ + const char *name) + + Add a new global variable of the given type and name to the context. + + +Working with pointers, structs and unions +----------------------------------------- + +.. function:: gcc_jit_lvalue *\ + gcc_jit_rvalue_dereference (gcc_jit_rvalue *rvalue,\ + gcc_jit_location *loc) + + Given an rvalue of pointer type ``T *``, dereferencing the pointer, + getting an lvalue of type ``T``. Analogous to: + + .. code-block:: c + + *(EXPR) + + in C. + +Field access is provided separately for both lvalues and rvalues. + +.. function:: gcc_jit_lvalue *\ + gcc_jit_lvalue_access_field (gcc_jit_lvalue *struct_,\ + gcc_jit_location *loc,\ + gcc_jit_field *field) + + Given an lvalue of struct or union type, access the given field, + getting an lvalue of the field's type. Analogous to: + + .. code-block:: c + + (EXPR).field = ...; + + in C. + +.. function:: gcc_jit_rvalue *\ + gcc_jit_rvalue_access_field (gcc_jit_rvalue *struct_,\ + gcc_jit_location *loc,\ + gcc_jit_field *field) + + Given an rvalue of struct or union type, access the given field + as an rvalue. Analogous to: + + .. code-block:: c + + (EXPR).field + + in C. + +.. function:: gcc_jit_lvalue *\ + gcc_jit_rvalue_dereference_field (gcc_jit_rvalue *ptr,\ + gcc_jit_location *loc,\ + gcc_jit_field *field) + + Given an rvalue of pointer type ``T *`` where T is of struct or union + type, access the given field as an lvalue. Analogous to: + + .. code-block:: c + + (EXPR)->field + + in C, itself equivalent to ``(*EXPR).FIELD``. + +.. function:: gcc_jit_lvalue *\ + gcc_jit_context_new_array_access (gcc_jit_context *ctxt,\ + gcc_jit_location *loc,\ + gcc_jit_rvalue *ptr,\ + gcc_jit_rvalue *index) + + Given an rvalue of pointer type ``T *``, get at the element `T` at + the given index, using standard C array indexing rules i.e. each + increment of ``index`` corresponds to ``sizeof(T)`` bytes. + Analogous to: + + .. code-block:: c + + PTR[INDEX] + + in C (or, indeed, to ``PTR + INDEX``). diff --git a/gcc/jit/docs/topics/functions.rst b/gcc/jit/docs/topics/functions.rst new file mode 100644 index 0000000..aa0c069 --- /dev/null +++ b/gcc/jit/docs/topics/functions.rst @@ -0,0 +1,311 @@ +.. Copyright (C) 2014 Free Software Foundation, Inc. + Originally contributed by David Malcolm + + This is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see + . + +.. default-domain:: c + +Creating and using functions +============================ + +Params +------ +.. type:: gcc_jit_param + + A `gcc_jit_param` represents a parameter to a function. + +.. function:: gcc_jit_param *\ + gcc_jit_context_new_param (gcc_jit_context *ctxt,\ + gcc_jit_location *loc,\ + gcc_jit_type *type,\ + const char *name) + + In preparation for creating a function, create a new parameter of the + given type and name. + +Parameters are lvalues, and thus are also rvalues (and objects), so the +following upcasts are available: + +.. function:: gcc_jit_lvalue *\ + gcc_jit_param_as_lvalue (gcc_jit_param *param) + + Upcasting from param to lvalue. + +.. function:: gcc_jit_rvalue *\ + gcc_jit_param_as_rvalue (gcc_jit_param *param) + + Upcasting from param to rvalue. + +.. function:: gcc_jit_object *\ + gcc_jit_param_as_object (gcc_jit_param *param) + + Upcasting from param to object. + + +Functions +--------- + +.. type:: gcc_jit_function + + A `gcc_jit_function` represents a function - either one that we're + creating ourselves, or one that we're referencing. + +.. function:: gcc_jit_function *\ + gcc_jit_context_new_function (gcc_jit_context *ctxt,\ + gcc_jit_location *loc,\ + enum gcc_jit_function_kind kind,\ + gcc_jit_type *return_type,\ + const char *name,\ + int num_params,\ + gcc_jit_param **params,\ + int is_variadic) + + Create a gcc_jit_function with the given name and parameters. + + .. type:: enum gcc_jit_function_kind + + This enum controls the kind of function created, and has the following + values: + + .. macro:: GCC_JIT_FUNCTION_EXPORTED + + Function is defined by the client code and visible + by name outside of the JIT. + + .. macro:: GCC_JIT_FUNCTION_INTERNAL + + Function is defined by the client code, but is invisible + outside of the JIT. Analogous to a "static" function. + + .. macro:: GCC_JIT_FUNCTION_IMPORTED + + Function is not defined by the client code; we're merely + referring to it. Analogous to using an "extern" function from a + header file. + + .. macro:: GCC_JIT_FUNCTION_ALWAYS_INLINE + + Function is only ever inlined into other functions, and is + invisible outside of the JIT. + + Analogous to prefixing with ``inline`` and adding + ``__attribute__((always_inline))`` + + Inlining will only occur when the optimization level is + above 0; when optimization is off, this is essentially the + same as GCC_JIT_FUNCTION_INTERNAL. + +.. function:: gcc_jit_function *\ + gcc_jit_context_get_builtin_function (gcc_jit_context *ctxt,\ + const char *name) + +.. function:: gcc_jit_object *\ + gcc_jit_function_as_object (gcc_jit_function *func) + + Upcasting from function to object. + +.. function:: gcc_jit_param *\ + gcc_jit_function_get_param (gcc_jit_function *func, int index) + + Get the param of the given index (0-based). + +.. function:: void \ + gcc_jit_function_dump_to_dot (gcc_jit_function *func,\ + const char *path) + + Emit the function in graphviz format to the given path. + +.. function:: gcc_jit_lvalue *\ + gcc_jit_function_new_local (gcc_jit_function *func,\ + gcc_jit_location *loc,\ + gcc_jit_type *type,\ + const char *name) + + Create a new local variable within the function, of the given type and + name. + + +Blocks +------ +.. type:: gcc_jit_block + + A `gcc_jit_block` represents a basic block within a function i.e. a + sequence of statements with a single entry point and a single exit + point. + + The first basic block that you create within a function will + be the entrypoint. + + Each basic block that you create within a function must be + terminated, either with a conditional, a jump, or a return. + + It's legal to have multiple basic blocks that return within + one function. + +.. function:: gcc_jit_block *\ + gcc_jit_function_new_block (gcc_jit_function *func,\ + const char *name) + + Create a basic block of the given name. The name may be NULL, but + providing meaningful names is often helpful when debugging: it may + show up in dumps of the internal representation, and in error + messages. + +.. function:: gcc_jit_object *\ + gcc_jit_block_as_object (gcc_jit_block *block) + + Upcast from block to object. + +.. function:: gcc_jit_function *\ + gcc_jit_block_get_function (gcc_jit_block *block) + + Which function is this block within? + + +Statements +---------- + +.. function:: void\ + gcc_jit_block_add_eval (gcc_jit_block *block,\ + gcc_jit_location *loc,\ + gcc_jit_rvalue *rvalue) + + Add evaluation of an rvalue, discarding the result + (e.g. a function call that "returns" void). + + This is equivalent to this C code: + + .. code-block:: c + + (void)expression; + +.. function:: void\ + gcc_jit_block_add_assignment (gcc_jit_block *block,\ + gcc_jit_location *loc,\ + gcc_jit_lvalue *lvalue,\ + gcc_jit_rvalue *rvalue) + + Add evaluation of an rvalue, assigning the result to the given + lvalue. + + This is roughly equivalent to this C code: + + .. code-block:: c + + lvalue = rvalue; + +.. function:: void\ + gcc_jit_block_add_assignment_op (gcc_jit_block *block,\ + gcc_jit_location *loc,\ + gcc_jit_lvalue *lvalue,\ + enum gcc_jit_binary_op op,\ + gcc_jit_rvalue *rvalue) + + Add evaluation of an rvalue, using the result to modify an + lvalue. + + This is analogous to "+=" and friends: + + .. code-block:: c + + lvalue += rvalue; + lvalue *= rvalue; + lvalue /= rvalue; + + etc. For example: + + .. code-block:: c + + /* "i++" */ + gcc_jit_block_add_assignment_op ( + loop_body, NULL, + i, + GCC_JIT_BINARY_OP_PLUS, + gcc_jit_context_one (ctxt, int_type)); + +.. function:: void\ + gcc_jit_block_add_comment (gcc_jit_block *block,\ + gcc_jit_location *loc,\ + const char *text) + + Add a no-op textual comment to the internal representation of the + code. It will be optimized away, but will be visible in the dumps + seen via :macro:`GCC_JIT_BOOL_OPTION_DUMP_INITIAL_TREE` + and :macro:`GCC_JIT_BOOL_OPTION_DUMP_INITIAL_GIMPLE`, + and thus may be of use when debugging how your project's internal + representation gets converted to the libgccjit IR. + +.. function:: void\ + gcc_jit_block_end_with_conditional (gcc_jit_block *block,\ + gcc_jit_location *loc,\ + gcc_jit_rvalue *boolval,\ + gcc_jit_block *on_true,\ + gcc_jit_block *on_false) + + Terminate a block by adding evaluation of an rvalue, branching on the + result to the appropriate successor block. + + This is roughly equivalent to this C code: + + .. code-block:: c + + if (boolval) + goto on_true; + else + goto on_false; + + block, boolval, on_true, and on_false must be non-NULL. + +.. function:: void\ + gcc_jit_block_end_with_jump (gcc_jit_block *block,\ + gcc_jit_location *loc,\ + gcc_jit_block *target) + + + Terminate a block by adding a jump to the given target block. + + This is roughly equivalent to this C code: + + .. code-block:: c + + goto target; + +.. function:: void\ + gcc_jit_block_end_with_return (gcc_jit_block *block,\ + gcc_jit_location *loc,\ + gcc_jit_rvalue *rvalue) + + + Terminate a block by adding evaluation of an rvalue, returning the value. + + This is roughly equivalent to this C code: + + .. code-block:: c + + return expression; + +.. function:: void\ + gcc_jit_block_end_with_void_return (gcc_jit_block *block,\ + gcc_jit_location *loc) + + + Terminate a block by adding a valueless return, for use within a function + with "void" return type. + + This is equivalent to this C code: + + .. code-block:: c + + return; diff --git a/gcc/jit/docs/topics/index.rst b/gcc/jit/docs/topics/index.rst new file mode 100644 index 0000000..a129137 --- /dev/null +++ b/gcc/jit/docs/topics/index.rst @@ -0,0 +1,30 @@ +.. Copyright (C) 2014 Free Software Foundation, Inc. + Originally contributed by David Malcolm + + This is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see + . + +Topic Reference +=============== + +.. toctree:: + :maxdepth: 2 + + contexts.rst + objects.rst + types.rst + expressions.rst + functions.rst + locations.rst + results.rst diff --git a/gcc/jit/docs/topics/locations.rst b/gcc/jit/docs/topics/locations.rst new file mode 100644 index 0000000..d1db974 --- /dev/null +++ b/gcc/jit/docs/topics/locations.rst @@ -0,0 +1,69 @@ +.. Copyright (C) 2014 Free Software Foundation, Inc. + Originally contributed by David Malcolm + + This is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see + . + +.. default-domain:: c + +Source Locations +================ + +.. type:: gcc_jit_location + + A `gcc_jit_location` encapsulates a source code location, so that + you can (optionally) associate locations in your language with + statements in the JIT-compiled code, allowing the debugger to + single-step through your language. + + `gcc_jit_location` instances are optional: you can always pass NULL to + any API entrypoint accepting one. + + You can construct them using :c:func:`gcc_jit_context_new_location`. + + You need to enable :c:macro:`GCC_JIT_BOOL_OPTION_DEBUGINFO` on the + :c:type:`gcc_jit_context` for these locations to actually be usable by + the debugger: + + .. code-block:: c + + gcc_jit_context_set_bool_option ( + ctxt, + GCC_JIT_BOOL_OPTION_DEBUGINFO, + 1); + +.. function:: gcc_jit_location *\ + gcc_jit_context_new_location (gcc_jit_context *ctxt,\ + const char *filename,\ + int line,\ + int column) + + Create a `gcc_jit_location` instance representing the given source + location. + +Faking it +--------- +If you don't have source code for your internal representation, but need +to debug, you can generate a C-like representation of the functions in +your context using :c:func:`gcc_jit_context_dump_to_file()`: + +.. code-block:: c + + gcc_jit_context_dump_to_file (ctxt, "/tmp/something.c", + 1 /* update_locations */); + +This will dump C-like code to the given path. If the `update_locations` +argument is true, this will also set up `gcc_jit_location` information +throughout the context, pointing at the dump file as if it were a source +file, giving you *something* you can step through in the debugger. diff --git a/gcc/jit/docs/topics/objects.rst b/gcc/jit/docs/topics/objects.rst new file mode 100644 index 0000000..b05888d --- /dev/null +++ b/gcc/jit/docs/topics/objects.rst @@ -0,0 +1,86 @@ +.. Copyright (C) 2014 Free Software Foundation, Inc. + Originally contributed by David Malcolm + + This is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see + . + +.. default-domain:: c + +Objects +======= + +.. type:: gcc_jit_object + +Almost every entity in the API (with the exception of +:c:type:`gcc_jit_context *` and :c:type:`gcc_jit_result *`) is a +"contextual" object, a :c:type:`gcc_jit_object *` + +A JIT object: + + * is associated with a :c:type:`gcc_jit_context *`. + + * is automatically cleaned up for you when its context is released so + you don't need to manually track and cleanup all objects, just the + contexts. + +Although the API is C-based, there is a form of class hierarchy, which +looks like this:: + + +- gcc_jit_object + +- gcc_jit_location + +- gcc_jit_type + +- gcc_jit_struct + +- gcc_jit_field + +- gcc_jit_function + +- gcc_jit_block + +- gcc_jit_rvalue + +- gcc_jit_lvalue + +- gcc_jit_param + +There are casting methods for upcasting from subclasses to parent classes. +For example, :c:func:`gcc_jit_type_as_object`: + +.. code-block:: c + + gcc_jit_object *obj = gcc_jit_type_as_object (int_type); + +The object "base class" has the following operations: + +.. function:: gcc_jit_context *gcc_jit_object_get_context (gcc_jit_object *obj) + + Which context is "obj" within? + + +.. function:: const char *gcc_jit_object_get_debug_string (gcc_jit_object *obj) + + Generate a human-readable description for the given object. + + For example, + + .. code-block:: c + + printf ("obj: %s\n", gcc_jit_object_get_debug_string (obj)); + + might give this text on stdout: + + .. code-block:: bash + + obj: 4.0 * (float)i + + .. note:: + + If you call this on an object, the `const char *` buffer is allocated + and generated on the first call for that object, and the buffer will + have the same lifetime as the object i.e. it will exist until the + object's context is released. diff --git a/gcc/jit/docs/topics/results.rst b/gcc/jit/docs/topics/results.rst new file mode 100644 index 0000000..10dc94f --- /dev/null +++ b/gcc/jit/docs/topics/results.rst @@ -0,0 +1,48 @@ +.. Copyright (C) 2014 Free Software Foundation, Inc. + Originally contributed by David Malcolm + + This is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see + . + +.. default-domain:: c + +Compilation results +=================== + +.. type:: gcc_jit_result + + A `gcc_jit_result` encapsulates the result of compiling a context. + +.. function:: gcc_jit_result *\ + gcc_jit_context_compile (gcc_jit_context *ctxt) + + This calls into GCC and builds the code, returning a + `gcc_jit_result *`. + + +.. function:: void *\ + gcc_jit_result_get_code (gcc_jit_result *result,\ + const char *funcname) + + Locate a given function within the built machine code. + This will need to be cast to a function pointer of the + correct type before it can be called. + + +.. function:: void\ + gcc_jit_result_release (gcc_jit_result *result) + + Once we're done with the code, this unloads the built .so file. + This cleans up the result; after calling this, it's no longer + valid to use the result. diff --git a/gcc/jit/docs/topics/types.rst b/gcc/jit/docs/topics/types.rst new file mode 100644 index 0000000..6770eca --- /dev/null +++ b/gcc/jit/docs/topics/types.rst @@ -0,0 +1,217 @@ +.. Copyright (C) 2014 Free Software Foundation, Inc. + Originally contributed by David Malcolm + + This is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see + . + +.. default-domain:: c + +Types +===== + +.. c:type:: gcc_jit_type + + gcc_jit_type represents a type within the library. + +.. function:: gcc_jit_object *gcc_jit_type_as_object (gcc_jit_type *type) + + Upcast a type to an object. + +Types can be created in several ways: + +* fundamental types can be accessed using + :func:`gcc_jit_context_get_type`: + + .. code-block:: c + + gcc_jit_type *int_type = gcc_jit_context_get_type (GCC_JIT_TYPE_INT); + + See :func:`gcc_jit_context_get_type` for the available types. + +* derived types can be accessed by using functions such as + :func:`gcc_jit_type_get_pointer` and :func:`gcc_jit_type_get_const`: + + .. code-block:: c + + gcc_jit_type *const_int_star = gcc_jit_type_get_pointer (gcc_jit_type_get_const (int_type)); + gcc_jit_type *int_const_star = gcc_jit_type_get_const (gcc_jit_type_get_pointer (int_type)); + +* by creating structures (see below). + +Standard types +-------------- + +.. function:: gcc_jit_type *gcc_jit_context_get_type (gcc_jit_context *ctxt, \ + enum gcc_jit_types type_) + + Access a specific type. The available types are: + + ========================================= ================================ + `enum gcc_jit_types` value Meaning + ========================================= ================================ + :c:data:`GCC_JIT_TYPE_VOID` C's ``void`` type. + :c:data:`GCC_JIT_TYPE_VOID_PTR` C's ``void *``. + :c:data:`GCC_JIT_TYPE_BOOL` C++'s ``bool`` type; also C99's + ``_Bool`` type, aka ``bool`` if + using stdbool.h. + :c:data:`GCC_JIT_TYPE_CHAR` C's ``char`` (of some signedness) + :c:data:`GCC_JIT_TYPE_SIGNED_CHAR` C's ``signed char`` + :c:data:`GCC_JIT_TYPE_UNSIGNED_CHAR` C's ``unsigned char`` + :c:data:`GCC_JIT_TYPE_SHORT` C's ``short`` (signed) + :c:data:`GCC_JIT_TYPE_UNSIGNED_SHORT` C's ``unsigned short`` + :c:data:`GCC_JIT_TYPE_INT` C's ``int`` (signed) + :c:data:`GCC_JIT_TYPE_UNSIGNED_INT` C's ``unsigned int`` + :c:data:`GCC_JIT_TYPE_LONG` C's ``long`` (signed) + :c:data:`GCC_JIT_TYPE_UNSIGNED_LONG` C's ``unsigned long`` + :c:data:`GCC_JIT_TYPE_LONG_LONG` C99's ``long long`` (signed) + :c:data:`GCC_JIT_TYPE_UNSIGNED_LONG_LONG` C99's ``unsigned long long`` + :c:data:`GCC_JIT_TYPE_FLOAT` + :c:data:`GCC_JIT_TYPE_DOUBLE` + :c:data:`GCC_JIT_TYPE_LONG_DOUBLE` + :c:data:`GCC_JIT_TYPE_CONST_CHAR_PTR` C type: ``(const char *)`` + :c:data:`GCC_JIT_TYPE_SIZE_T` C's ``size_t`` type + :c:data:`GCC_JIT_TYPE_FILE_PTR` C type: ``(FILE *)`` + ========================================= ================================ + +.. function:: gcc_jit_type *\ + gcc_jit_context_get_int_type (gcc_jit_context *ctxt, \ + int num_bytes, int is_signed) + + Access the integer type of the given size. + + +Pointers, `const`, and `volatile` +--------------------------------- + +.. function:: gcc_jit_type *gcc_jit_type_get_pointer (gcc_jit_type *type) + + Given type "T", get type "T*". + +.. function:: gcc_jit_type *gcc_jit_type_get_const (gcc_jit_type *type) + + Given type "T", get type "const T". + +.. function:: gcc_jit_type *gcc_jit_type_get_volatile (gcc_jit_type *type) + + Given type "T", get type "volatile T". + +.. function:: gcc_jit_type *\ + gcc_jit_context_new_array_type (gcc_jit_context *ctxt, \ + gcc_jit_location *loc, \ + gcc_jit_type *element_type, \ + int num_elements) + + Given type "T", get type "T[N]" (for a constant N). + + +Structures and unions +--------------------- + +.. c:type:: gcc_jit_struct + +A compound type analagous to a C `struct`. + +.. c:type:: gcc_jit_field + +A field within a :c:type:`gcc_jit_struct`. + +You can model C `struct` types by creating :c:type:`gcc_jit_struct *` and +:c:type:`gcc_jit_field` instances, in either order: + +* by creating the fields, then the structure. For example, to model: + + .. code-block:: c + + struct coord {double x; double y; }; + + you could call: + + .. code-block:: c + + gcc_jit_field *field_x = + gcc_jit_context_new_field (ctxt, NULL, double_type, "x"); + gcc_jit_field *field_y = + gcc_jit_context_new_field (ctxt, NULL, double_type, "y"); + gcc_jit_field *fields[2] = {field_x, field_y}; + gcc_jit_struct *coord = + gcc_jit_context_new_struct_type (ctxt, NULL, "coord", 2, fields); + +* by creating the structure, then populating it with fields, typically + to allow modelling self-referential structs such as: + + .. code-block:: c + + struct node { int m_hash; struct node *m_next; }; + + like this: + + .. code-block:: c + + gcc_jit_type *node = + gcc_jit_context_new_opaque_struct (ctxt, NULL, "node"); + gcc_jit_type *node_ptr = + gcc_jit_type_get_pointer (node); + gcc_jit_field *field_hash = + gcc_jit_context_new_field (ctxt, NULL, int_type, "m_hash"); + gcc_jit_field *field_next = + gcc_jit_context_new_field (ctxt, NULL, node_ptr, "m_next"); + gcc_jit_field *fields[2] = {field_hash, field_next}; + gcc_jit_struct_set_fields (node, NULL, 2, fields); + +.. function:: gcc_jit_field *\ + gcc_jit_context_new_field (gcc_jit_context *ctxt,\ + gcc_jit_location *loc,\ + gcc_jit_type *type,\ + const char *name) + + Construct a new field, with the given type and name. + +.. function:: gcc_jit_object *\ + gcc_jit_field_as_object (gcc_jit_field *field) + + Upcast from field to object. + +.. function:: gcc_jit_struct *\ + gcc_jit_context_new_struct_type (gcc_jit_context *ctxt,\ + gcc_jit_location *loc,\ + const char *name,\ + int num_fields,\ + gcc_jit_field **fields) + + Construct a new struct type, with the given name and fields. + +.. function:: gcc_jit_struct *\ + gcc_jit_context_new_opaque_struct (gcc_jit_context *ctxt,\ + gcc_jit_location *loc,\ + const char *name) + + Construct a new struct type, with the given name, but without + specifying the fields. The fields can be omitted (in which case the + size of the struct is not known), or later specified using + :c:func:`gcc_jit_struct_set_fields`. + +.. function:: gcc_jit_type *\ + gcc_jit_struct_as_type (gcc_jit_struct *struct_type) + + Upcast from struct to type. + +.. function:: void\ + gcc_jit_struct_set_fields (gcc_jit_struct *struct_type,\ + gcc_jit_location *loc,\ + int num_fields,\ + gcc_jit_field **fields) + + Populate the fields of a formerly-opaque struct type. + + This can only be called once on a given struct type. -- 1.8.5.3