47#define MAX_RECURSION_DEPTH 32
49#define MAX_PRINT_RECURSION_DEPTH 128
53 size_t * out_num_args,
54 size_t * out_num_fixed_args);
74 while (isspace((
unsigned char)*state->
p))
77 while (*state->
p !=
'\n' && *state->
p !=
'\0')
91 const char *
start = state->
p;
94 unsigned long long val = strtoull(
start, &
end, 10);
97 if (
end ==
start || errno == ERANGE) {
104 if (val > SIZE_MAX) {
112 if (val == (
unsigned long long)SIZE_MAX) {
116 *out_val = (size_t)val;
130 const char *
start = state->
p;
131 if (!isalpha((
unsigned char)*
start) && *
start !=
'_')
133 while (isalnum((
unsigned char)*state->
p) || *state->
p ==
'_' || *state->
p ==
':') {
134 if (*state->
p ==
':' && state->
p[1] !=
':')
136 if (*state->
p ==
':')
140 size_t len = state->
p -
start;
164 size_t len = strlen(keyword);
165 if (strncmp(state->
p, keyword, len) == 0) {
167 if (isalnum((
unsigned char)state->
p[len]) || state->
p[len] ==
'_')
187 const char * p_before = state->
p;
191 if (*state->
p ==
':') {
215 const char *
p = state->
p;
221 while (*
p !=
'\0' && depth > 0) {
231 while (isspace((
unsigned char)*
p) || *
p ==
'#') {
233 while (*
p !=
'\n' && *
p !=
'\0')
239 return (
p[0] ==
'-' &&
p[1] ==
'>');
255 typedef struct member_node {
257 struct member_node * next;
259 member_node *head =
nullptr, *tail =
nullptr;
260 size_t num_members = 0;
262 if (*state->
p != end_char) {
264 const char * p_before_member = state->
p;
267 if (name && (*state->
p ==
',' || *state->
p == end_char)) {
268 state->
p = p_before_member + strlen(name);
282 uint8_t bit_width = 0;
283 bool is_bitfield =
false;
284 const char * p_before_colon = state->
p;
286 if (*state->
p ==
':') {
289 if (!isdigit((
unsigned char)*state->
p)) {
291 state->
p = p_before_colon;
294 size_t width_val = 0;
297 size_t type_bits = member_type->
size * 8;
300 if (type_bits == 0 || type_bits > 255)
302 if (width_val > type_bits) {
306 bit_width = (uint8_t)width_val;
324 node->next =
nullptr;
335 if (*state->
p ==
',') {
339 if (*state->
p == end_char) {
344 else if (*state->
p == end_char)
347 if (*state->
p ==
'\0') {
356 *out_num_members = num_members;
357 if (num_members == 0)
366 member_node * current = head;
367 for (
size_t i = 0; i < num_members; i++) {
369 current = current->next;
387 if (*state->
p != start_char) {
393 size_t num_members = 0;
400 if (*state->
p != end_char) {
423 size_t alignment = 1;
424 if (*state->
p ==
'!') {
426 if (isdigit((
unsigned char)*state->
p)) {
430 if (*state->
p !=
':') {
438 if (*state->
p !=
'{') {
443 size_t num_members = 0;
447 if (*state->
p !=
'}') {
458 size_t total_size = 0;
459 for (
size_t i = 0; i < num_members; ++i)
460 total_size +=
members[i].type->size;
483 size_t len = strlen(name) + 1;
487 t->
name = arena_name;
642 size_t current_offset = state->
p - state->
start;
644 const char * p_before_type = state->
p;
645 if (*state->
p ==
'@') {
655 result_type =
nullptr;
657 else if (*state->
p ==
'*') {
666 result_type =
nullptr;
668 else if (*state->
p ==
'(') {
672 size_t num_args = 0, num_fixed = 0;
686 func_type->
size =
sizeof(
void *);
694 result_type = func_type;
705 if (*state->
p !=
')') {
707 result_type =
nullptr;
713 else if (*state->
p ==
'[') {
716 size_t num_elements = 0;
717 bool is_flexible =
false;
719 if (*state->
p ==
'?') {
730 if (*state->
p !=
':') {
748 if (*state->
p !=
']') {
757 result_type =
nullptr;
761 result_type =
nullptr;
764 else if (*state->
p ==
'!')
766 else if (*state->
p ==
'{')
768 else if (*state->
p ==
'<')
770 else if (*state->
p ==
'e' && state->
p[1] ==
':') {
780 result_type =
nullptr;
782 else if (*state->
p ==
'c' && state->
p[1] ==
'[') {
791 if (*state->
p !=
']') {
798 result_type =
nullptr;
800 else if (*state->
p ==
'v' && state->
p[1] ==
'[') {
808 if (*state->
p !=
':') {
819 if (*state->
p !=
']') {
826 result_type =
nullptr;
833 state->
p = p_before_type;
834 if (isalpha((
unsigned char)*state->
p) || *state->
p ==
'_')
863 size_t * out_num_args,
864 size_t * out_num_fixed_args) {
865 if (*state->
p !=
'(') {
872 typedef struct arg_node {
874 struct arg_node * next;
876 arg_node *head =
nullptr, *tail =
nullptr;
879 if (*state->
p !=
')' && *state->
p !=
';') {
882 if (*state->
p ==
')' || *state->
p ==
';')
894 node->arg.type = arg_type;
895 node->arg.name = name;
896 node->next =
nullptr;
905 if (*state->
p ==
',') {
908 if (*state->
p ==
')' || *state->
p ==
';') {
913 else if (*state->
p !=
')' && *state->
p !=
';') {
921 *out_num_fixed_args = num_args;
923 if (*state->
p ==
';') {
925 if (*state->
p !=
')') {
928 if (*state->
p ==
')')
940 node->arg.type = arg_type;
941 node->arg.name = name;
942 node->next =
nullptr;
951 if (*state->
p ==
',') {
954 if (*state->
p ==
')') {
959 else if (*state->
p !=
')') {
969 if (*state->
p !=
')') {
976 if (state->
p[0] !=
'-' || state->
p[1] !=
'>') {
988 if (num_args > 0 && !
args) {
992 arg_node * current = head;
993 for (
size_t i = 0; i < num_args; i++) {
994 args[i] = current->arg;
995 current = current->next;
998 *out_num_args = num_args;
1020 const char * signature) {
1021 if (!out_type || !out_arena) {
1025 if (!signature || *signature ==
'\0') {
1035 parser_state state = {.
p = signature, .start = signature, .arena = *out_arena, .depth = 0};
1040 if (state.
p[0] !=
'\0') {
1048 *out_arena =
nullptr;
1049 *out_type =
nullptr;
1070 const char * signature,
1092 *out_arena =
nullptr;
1100 *out_arena =
nullptr;
1101 *out_type =
nullptr;
1106 *out_type = final_type;
1131 size_t * out_num_args,
1132 size_t * out_num_fixed_args,
1141 if (*signature ==
'\0') {
1145 if (!out_arena || !out_ret_type || !out_args || !out_num_args || !out_num_fixed_args) {
1176 if (!final_func_type) {
1178 *out_arena =
nullptr;
1187 *out_arena =
nullptr;
1211 const void * itanium_subs[64];
1230 va_start(
args, fmt);
1233 if (written < 0 || (
size_t)written >= state->
remaining)
1237 state->
p += written;
1253#define PRINT_RECURSE(state, fn, arg) \
1255 if ((state)->depth >= MAX_PRINT_RECURSION_DEPTH) { \
1256 (state)->status = INFIX_ERROR_INVALID_ARGUMENT; \
1260 fn((state), (arg)); \
1295 int digit = val % 36;
1296 buf[pos++] = (digit < 10) ? (
char)(
'0' + digit) : (char)(
'A' + digit - 10);
1300 _print(state,
"%c", buf[--pos]);
1430 bool printed_alias =
false;
1432 if (num_elements == 8 &&
is_double(element_type)) {
1434 printed_alias =
true;
1436 else if (num_elements == 16 &&
is_float(element_type)) {
1438 printed_alias =
true;
1442 printed_alias =
true;
1444 else if (num_elements == 4 &&
is_double(element_type)) {
1446 printed_alias =
true;
1448 else if (num_elements == 8 &&
is_float(element_type)) {
1450 printed_alias =
true;
1453 if (!printed_alias) {
1454 _print(state,
"v[%zu:", num_elements);
1490 _print(state,
"sint128");
1493 _print(state,
"uint128");
1496 _print(state,
"float16");
1505 _print(state,
"longdouble");
1602 size_t len = strlen(name);
1603 _print(state,
"%zu%s", len, name);
1612 const char *
p = type->
name;
1616 if (
p[0] ==
':' &&
p[1] ==
':') {
1630 const char *
end = strstr(
p,
"::");
1631 size_t part_len =
end ? (size_t)(
end -
p) : strlen(
p);
1632 _print(state,
"%zu", part_len);
1634 for (
size_t i = 0; i < part_len; i++)
1645 size_t len = strlen(type->
name);
1770 if (strstr(type->
name,
"::")) {
1771 _print(state,
"%c", prefix);
1780 const char *
p = type->
name;
1783 const char *
end = strstr(
p,
"::");
1785 lens[count] =
end -
p;
1789 lens[count] = strlen(
p);
1796 for (
int i = count - 1; i >= 0; i--) {
1797 for (
size_t j = 0; j < lens[i]; j++)
1798 _print(state,
"%c", parts[i][j]);
1842 _print(state,
"U_Complex@@");
1979 _print(state,
"sint128");
1982 _print(state,
"uint128");
1985 _print(state,
"float16");
1994 _print(state,
"longdouble");
2026 buffer[buffer_size - 1] =
'\0';
2042 if (!buffer || buffer_size == 0 || !type) {
2055 _print(&state,
"unsupported_dialect");
2063 buffer[buffer_size - 1] =
'\0';
2067 else if (buffer_size > 0)
2069 buffer[buffer_size - 1] =
'\0';
2086 const char * function_name,
2090 size_t num_fixed_args,
2093 if (!buffer || buffer_size == 0 || !
ret_type || (num_args > 0 && !
args)) {
2100 (void)function_name;
2102 for (
size_t i = 0; i < num_fixed_args; ++i) {
2107 if (num_args > num_fixed_args) {
2109 for (
size_t i = num_fixed_args; i < num_args; ++i) {
2110 if (i > num_fixed_args)
2123 if (function_name) {
2125 const char *
p = function_name;
2128 if (
p[0] ==
':' &&
p[1] ==
':') {
2140 const char *
end = strstr(
p,
"::");
2141 size_t part_len =
end ? (size_t)(
end -
p) : strlen(
p);
2142 _print(&state,
"%zu", part_len);
2143 for (
size_t i = 0; i < part_len; i++)
2153 size_t name_len = strlen(function_name);
2154 _print(&state,
"%zu%s", name_len, function_name);
2163 for (
size_t i = 0; i < num_args; ++i)
2169 if (function_name) {
2171 if (strstr(function_name,
"::")) {
2175 const char *
p = function_name;
2178 const char *
end = strstr(
p,
"::");
2180 lens[count] =
end -
p;
2184 lens[count] = strlen(
p);
2190 for (
int i = count - 1; i >= 0; i--) {
2191 for (
size_t j = 0; j < lens[i]; j++)
2192 _print(&state,
"%c", parts[i][j]);
2197 _print(&state,
"%s@", function_name);
2209 for (
size_t i = 0; i < num_args; ++i)
2214 _print(&state,
"unsupported_dialect");
2221 if (buffer_size > 0)
2222 buffer[buffer_size - 1] =
'\0';
2226 else if (buffer_size > 0)
2227 buffer[buffer_size - 1] =
'\0';
2245 if (!buffer || buffer_size == 0 || !
registry)
2253 if (entry->type && !entry->is_forward_declaration) {
2254 char type_body_buffer[1024];
2259 goto end_print_loop;
2261 _print(&state,
"@%s = %s;\n", entry->name, type_body_buffer);
2263 else if (entry->is_forward_declaration)
2264 _print(&state,
"@%s;\n", entry->name);
2266 goto end_print_loop;
infix_registry_t * registry
Definition 008_registry_introspection.c:33
infix_status status
Definition 103_unions.c:61
infix_struct_member * members
Definition 103_unions.c:55
void * args[]
Definition 202_in_structs.c:59
clock_t start
Definition 901_call_overhead.c:48
infix_type * ret_type
Definition 901_call_overhead.c:61
clock_t end
Definition 901_call_overhead.c:48
char * p
Definition 904_registry_benchmark.c:25
#define c23_nodiscard
Internal alias for the public INFIX_NODISCARD macro.
Definition compat_c23.h:92
#define INFIX_TLS
Definition error.c:68
INFIX_API infix_error_details_t infix_get_last_error(void)
Retrieves detailed information about the last error that occurred on the current thread.
Definition error.c:281
infix_error_code_t
Enumerates specific error codes.
Definition infix.h:1412
@ INFIX_CODE_SUCCESS
Definition infix.h:1414
@ INFIX_CODE_INVALID_MEMBER_TYPE
Definition infix.h:1440
@ INFIX_CODE_INTEGER_OVERFLOW
Definition infix.h:1431
@ INFIX_CODE_TYPE_TOO_LARGE
Definition infix.h:1438
@ INFIX_CODE_EMPTY_SIGNATURE
Definition infix.h:1434
@ INFIX_CODE_UNEXPECTED_TOKEN
Definition infix.h:1427
@ INFIX_CODE_MISSING_RETURN_TYPE
Definition infix.h:1430
@ INFIX_CODE_RECURSION_DEPTH_EXCEEDED
Definition infix.h:1432
@ INFIX_CODE_UNTERMINATED_AGGREGATE
Definition infix.h:1428
@ INFIX_CODE_NULL_POINTER
Definition infix.h:1416
@ INFIX_CODE_INVALID_KEYWORD
Definition infix.h:1429
@ INFIX_CODE_OUT_OF_MEMORY
Definition infix.h:1421
@ INFIX_CATEGORY_ALLOCATION
Definition infix.h:1405
@ INFIX_CATEGORY_GENERAL
Definition infix.h:1404
@ INFIX_CATEGORY_PARSER
Definition infix.h:1406
size_t source_offset
Definition infix.h:284
struct infix_type_t::@0::@1 pointer_info
Metadata for INFIX_TYPE_POINTER.
union infix_type_t::@0 meta
A union containing metadata specific to the type's category.
bool is_packed
Definition infix.h:297
struct infix_type_t::@0::@7 vector_info
Metadata for INFIX_TYPE_VECTOR.
infix_type * type
Definition infix.h:352
c23_nodiscard infix_status infix_signature_parse(const char *signature, infix_arena_t **out_arena, infix_type **out_ret_type, infix_function_argument **out_args, size_t *out_num_args, size_t *out_num_fixed_args, infix_registry_t *registry)
Parses a full function signature string into its constituent parts.
Definition signature.c:1127
struct infix_type_t::@0::@4 func_ptr_info
Metadata for INFIX_TYPE_REVERSE_TRAMPOLINE.
size_t num_elements
Definition infix.h:302
infix_arena_t * arena
Definition infix.h:283
size_t size
Definition infix.h:279
size_t alignment
Definition infix.h:280
infix_struct_member * members
Definition infix.h:295
struct infix_type_t::@0::@6 complex_info
Metadata for INFIX_TYPE_COMPLEX.
c23_nodiscard infix_status infix_type_from_signature(infix_type **out_type, infix_arena_t **out_arena, const char *signature, infix_registry_t *registry)
Parses a signature string representing a single data type.
Definition signature.c:1068
const char * name
Definition infix.h:277
infix_function_argument * args
Definition infix.h:308
infix_status
Enumerates the possible status codes returned by infix API functions.
Definition infix.h:486
const char * name
Definition infix.h:351
const char * name
Definition infix.h:337
infix_type_category category
Definition infix.h:278
struct infix_type_t::@0::@2 aggregate_info
Metadata for INFIX_TYPE_STRUCT and INFIX_TYPE_UNION.
struct infix_type_t::@0::@3 array_info
Metadata for INFIX_TYPE_ARRAY.
struct infix_type_t * pointee_type
Definition infix.h:291
infix_type * type
Definition infix.h:338
struct infix_type_t * element_type
Definition infix.h:301
bool is_flexible
Definition infix.h:303
struct infix_type_t * return_type
Definition infix.h:307
struct infix_type_t::@0::@5 enum_info
Metadata for INFIX_TYPE_ENUM.
struct infix_type_t * base_type
Definition infix.h:318
uint8_t bit_width
Definition infix.h:341
size_t num_members
Definition infix.h:296
struct infix_type_t * underlying_type
Definition infix.h:314
struct infix_type_t::@0::@8 named_reference
Metadata for INFIX_TYPE_NAMED_REFERENCE.
size_t num_fixed_args
Definition infix.h:310
infix_primitive_type_id primitive_id
Metadata for INFIX_TYPE_PRIMITIVE.
Definition infix.h:288
size_t num_args
Definition infix.h:309
bool is_arena_allocated
Definition infix.h:281
@ INFIX_ERROR_ALLOCATION_FAILED
Definition infix.h:488
@ INFIX_SUCCESS
Definition infix.h:487
@ INFIX_ERROR_INVALID_ARGUMENT
Definition infix.h:489
INFIX_API c23_nodiscard infix_status infix_function_print(char *buffer, size_t buffer_size, const char *function_name, const infix_type *ret_type, const infix_function_argument *args, size_t num_args, size_t num_fixed_args, infix_print_dialect_t dialect)
Serializes a function signature's components into a string.
Definition signature.c:2084
INFIX_API c23_nodiscard infix_status infix_type_print(char *buffer, size_t buffer_size, const infix_type *type, infix_print_dialect_t dialect)
Serializes an infix_type object graph back into a signature string.
Definition signature.c:2037
infix_print_dialect_t
Specifies the output format for printing types and function signatures.
Definition infix.h:1227
@ INFIX_DIALECT_SIGNATURE
Definition infix.h:1228
@ INFIX_DIALECT_ITANIUM_MANGLING
Definition infix.h:1229
@ INFIX_DIALECT_MSVC_MANGLING
Definition infix.h:1230
INFIX_API INFIX_NODISCARD void * infix_arena_alloc(infix_arena_t *, size_t, size_t)
Allocates a block of memory from an arena.
Definition arena.c:117
#define infix_memcpy
A macro that can be defined to override the default memcpy function.
Definition infix.h:439
INFIX_API INFIX_NODISCARD infix_arena_t * infix_arena_create(size_t)
Creates a new memory arena.
Definition arena.c:52
INFIX_API INFIX_NODISCARD void * infix_arena_calloc(infix_arena_t *, size_t, size_t, size_t)
Allocates and zero-initializes a block of memory from an arena.
Definition arena.c:188
INFIX_API void infix_arena_destroy(infix_arena_t *)
Destroys an arena and frees all memory allocated from it.
Definition arena.c:83
c23_nodiscard infix_status infix_registry_print(char *buffer, size_t buffer_size, const infix_registry_t *registry)
Serializes all defined types within a registry into a single, human-readable string.
Definition signature.c:2244
INFIX_API INFIX_NODISCARD infix_status infix_type_create_pointer_to(infix_arena_t *, infix_type **, infix_type *)
Creates a new pointer type that points to a specific type.
Definition types.c:399
INFIX_API infix_struct_member infix_type_create_member(const char *, infix_type *, size_t)
A factory function to create an infix_struct_member.
Definition types.c:208
INFIX_API INFIX_NODISCARD infix_status infix_type_create_packed_struct(infix_arena_t *, infix_type **, size_t, size_t, infix_struct_member *, size_t)
Creates a new packed struct type with a user-specified layout.
Definition types.c:725
INFIX_API INFIX_NODISCARD infix_status infix_type_create_complex(infix_arena_t *, infix_type **, infix_type *)
Creates a new _Complex number type.
Definition types.c:548
infix_primitive_type_id
Enumerates the supported primitive C types.
Definition infix.h:245
INFIX_API INFIX_NODISCARD infix_type * infix_type_create_void(void)
Creates a static descriptor for the void type.
Definition types.c:200
INFIX_API INFIX_NODISCARD infix_status infix_type_create_union(infix_arena_t *, infix_type **, infix_struct_member *, size_t)
Creates a new union type from an array of members.
Definition types.c:618
INFIX_API infix_struct_member infix_type_create_bitfield_member(const char *, infix_type *, size_t, uint8_t)
A factory function to create a bitfield infix_struct_member.
Definition types.c:219
INFIX_API INFIX_NODISCARD infix_status infix_type_create_named_reference(infix_arena_t *, infix_type **, const char *, infix_aggregate_category_t)
Creates a placeholder for a named type to be resolved by a registry.
Definition types.c:788
INFIX_API INFIX_NODISCARD infix_type * infix_type_create_primitive(infix_primitive_type_id)
Creates a static descriptor for a primitive C type.
Definition types.c:144
INFIX_API INFIX_NODISCARD infix_status infix_type_create_vector(infix_arena_t *, infix_type **, infix_type *, size_t)
Creates a new SIMD vector type.
Definition types.c:579
INFIX_API INFIX_NODISCARD infix_status infix_type_create_struct(infix_arena_t *, infix_type **, infix_struct_member *, size_t)
Creates a new struct type from an array of members, calculating layout automatically.
Definition types.c:666
INFIX_API INFIX_NODISCARD infix_status infix_type_create_enum(infix_arena_t *, infix_type **, infix_type *)
Creates a new enum type with a specified underlying integer type.
Definition types.c:513
INFIX_API infix_status infix_type_create_flexible_array(infix_arena_t *, infix_type **, infix_type *)
Creates a flexible array member type ([?:type]).
Definition types.c:469
INFIX_API INFIX_NODISCARD infix_status infix_type_create_array(infix_arena_t *, infix_type **, infix_type *, size_t)
Creates a new fixed-size array type.
Definition types.c:430
@ INFIX_PRIMITIVE_UINT16
Definition infix.h:249
@ INFIX_PRIMITIVE_UINT32
Definition infix.h:251
@ INFIX_PRIMITIVE_LONG_DOUBLE
Definition infix.h:260
@ INFIX_PRIMITIVE_FLOAT
Definition infix.h:258
@ INFIX_PRIMITIVE_DOUBLE
Definition infix.h:259
@ INFIX_PRIMITIVE_SINT16
Definition infix.h:250
@ INFIX_PRIMITIVE_SINT64
Definition infix.h:254
@ INFIX_PRIMITIVE_SINT32
Definition infix.h:252
@ INFIX_PRIMITIVE_UINT8
Definition infix.h:247
@ INFIX_PRIMITIVE_UINT128
Definition infix.h:255
@ INFIX_PRIMITIVE_BOOL
Definition infix.h:246
@ INFIX_PRIMITIVE_UINT64
Definition infix.h:253
@ INFIX_PRIMITIVE_FLOAT16
Definition infix.h:257
@ INFIX_PRIMITIVE_SINT128
Definition infix.h:256
@ INFIX_PRIMITIVE_SINT8
Definition infix.h:248
@ INFIX_TYPE_UNION
Definition infix.h:233
@ INFIX_TYPE_PRIMITIVE
Definition infix.h:230
@ INFIX_TYPE_COMPLEX
Definition infix.h:237
@ INFIX_TYPE_ARRAY
Definition infix.h:234
@ INFIX_TYPE_VECTOR
Definition infix.h:238
@ INFIX_TYPE_VOID
Definition infix.h:240
@ INFIX_TYPE_POINTER
Definition infix.h:231
@ INFIX_TYPE_NAMED_REFERENCE
Definition infix.h:239
@ INFIX_TYPE_REVERSE_TRAMPOLINE
Definition infix.h:235
@ INFIX_TYPE_ENUM
Definition infix.h:236
@ INFIX_TYPE_STRUCT
Definition infix.h:232
@ INFIX_AGGREGATE_STRUCT
Definition infix.h:266
#define INFIX_API
Symbol visibility macro.
Definition infix.h:114
#define INFIX_INTERNAL
When compiling with -fvisibility=hidden, we use this to explicitly mark internal-but-shared functions...
Definition infix_config.h:232
Internal data structures, function prototypes, and constants.
INFIX_INTERNAL c23_nodiscard infix_status _infix_resolve_type_graph_inplace(infix_type **type_ptr, infix_registry_t *registry)
Resolves all named type references in a type graph in-place.
Definition type_registry.c:428
static bool is_double(const infix_type *type)
A fast inline check to determine if an infix_type is a double.
Definition infix_internals.h:799
INFIX_INTERNAL infix_type * _copy_type_graph_to_arena(infix_arena_t *, const infix_type *)
Performs a deep copy of a type graph into a destination arena.
Definition types.c:1128
INFIX_INTERNAL void _infix_type_recalculate_layout(infix_type *type)
Recalculates the layout of a fully resolved type graph.
Definition types.c:940
INFIX_INTERNAL void _infix_clear_error(void)
Clears the thread-local error state.
Definition error.c:268
static bool is_float(const infix_type *type)
A fast inline check to determine if an infix_type is a float (32-bit).
Definition infix_internals.h:791
INFIX_INTERNAL void _infix_set_error(infix_error_category_t category, infix_error_code_t code, size_t position)
Sets the thread-local error state with detailed information.
Definition error.c:175
static void _print(printer_state *state, const char *fmt,...)
Definition signature.c:1226
static void _add_itanium_sub(printer_state *state, const void *component)
Definition signature.c:1275
static infix_struct_member * parse_aggregate_members(parser_state *state, char end_char, size_t *out_num_members)
Definition signature.c:253
static bool is_function_signature_ahead(const parser_state *state)
Definition signature.c:214
static void _infix_type_print_body_only_recursive(printer_state *state, const infix_type *type)
Definition signature.c:1874
c23_nodiscard infix_status _infix_type_print_body_only(char *buffer, size_t buffer_size, const infix_type *type, infix_print_dialect_t dialect)
An internal-only function to serialize a type's body without its registered name.
Definition signature.c:2014
INFIX_INTERNAL infix_type * parse_primitive(parser_state *state)
Definition signature.c:502
#define MAX_RECURSION_DEPTH
Definition signature.c:47
static bool _find_itanium_sub(printer_state *state, const void *component, size_t *index)
Definition signature.c:1265
INFIX_INTERNAL void skip_whitespace(parser_state *state)
Definition signature.c:72
static bool parse_size_t(parser_state *state, size_t *out_val)
Definition signature.c:90
c23_nodiscard infix_status _infix_parse_type_internal(infix_type **out_type, infix_arena_t **out_arena, const char *signature)
The internal core of the signature parser.
Definition signature.c:1018
static void _print_itanium_sub(printer_state *state, size_t index)
Definition signature.c:1280
static infix_status parse_function_signature_details(parser_state *state, infix_type **out_ret_type, infix_function_argument **out_args, size_t *out_num_args, size_t *out_num_fixed_args)
Definition signature.c:860
INFIX_INTERNAL void _infix_set_parser_error(parser_state *state, infix_error_code_t code)
Definition signature.c:62
static infix_type * _create_named_primitive(parser_state *state, infix_primitive_type_id id, const char *name)
Definition signature.c:474
static bool consume_keyword(parser_state *state, const char *keyword)
Definition signature.c:162
static infix_type * parse_packed_struct(parser_state *state)
Definition signature.c:422
#define PRINT_RECURSE(state, fn, arg)
Recursively prints a type with a depth guard.
Definition signature.c:1253
static infix_type * parse_aggregate(parser_state *state, char start_char, char end_char)
Definition signature.c:381
static const char * parse_identifier(parser_state *state)
Definition signature.c:128
INFIX_INTERNAL infix_type * parse_type(parser_state *state)
Definition signature.c:634
static void _infix_type_print_itanium_recursive(printer_state *state, const infix_type *type)
Definition signature.c:1520
static void _infix_type_print_signature_recursive(printer_state *state, const infix_type *type)
Definition signature.c:1318
static const char * parse_optional_name_prefix(parser_state *state)
Definition signature.c:184
INFIX_TLS const char * g_infix_last_signature_context
A thread-local pointer to the full signature string being parsed.
Definition error.c:99
static void _infix_type_print_msvc_recursive(printer_state *state, const infix_type *type)
Definition signature.c:1678
A single entry in the registry's hash table.
Definition infix_internals.h:174
Internal definition of a memory arena.
Definition infix_internals.h:143
Describes a single argument to a C function.
Definition infix.h:350
Internal definition of a named type registry.
Definition infix_internals.h:188
_infix_registry_entry_t ** buckets
Definition infix_internals.h:193
size_t num_buckets
Definition infix_internals.h:191
Describes a single member of a C struct or union.
Definition infix.h:336
A semi-opaque structure that describes a C type.
Definition infix.h:276
Holds the complete state of the recursive descent parser during a single parse operation.
Definition infix_internals.h:199
const char * start
Definition infix_internals.h:201
infix_arena_t * arena
Definition infix_internals.h:202
int depth
Definition infix_internals.h:203
const char * p
Definition infix_internals.h:200
Definition signature.c:1206
size_t depth
Definition signature.c:1216
char * p
Definition signature.c:1207
size_t remaining
Definition signature.c:1208
infix_status status
Definition signature.c:1209
const void * itanium_subs[64]
Definition signature.c:1211
size_t msvc_type_count
Definition signature.c:1215
const infix_type * msvc_types[10]
Definition signature.c:1214
size_t itanium_sub_count
Definition signature.c:1212