authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2024-12-24 14:47:15-08:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2024-12-24 14:53:35-08:00
logbf3f63a34a2e3101bf44bffd07c2e045aae8a834
tree21e347b138fca820d7356400a869fee52d02799d
parentaf5e731729592af4a5716edd3b1e03264d66ea46

delete aro dependency

translate-c is moving towards a package provided by the build system (#20630). The repository https://github.com/ziglang/translate-c/ implements C translation using Aro. This commit deletes the Aro implementation of C translation from the Zig repository, leaving only the Clang implementation. The other dependency on Aro is for the preprocessor. This must move to `std.zig.Preprocessor`, be untangled from Aro, and independently maintained. There must also be added a Preprocessor Build Step, which this commit does not do. Furthermore, the preprocessor must be exposed as a zig compiler JIT command rather than always being compiled into the compiler. This will reduce binary size and time spent waiting for zig to build.

89 files changed, 9228 insertions(+), 57313 deletions(-)

CMakeLists.txt+7-6
...@@ -532,13 +532,13 @@ set(ZIG_STAGE2_SOURCES...@@ -532,13 +532,13 @@ set(ZIG_STAGE2_SOURCES
532 src/arch/arm/Mir.zig532 src/arch/arm/Mir.zig
533 src/arch/arm/abi.zig533 src/arch/arm/abi.zig
534 src/arch/arm/bits.zig534 src/arch/arm/bits.zig
535 src/arch/riscv64/abi.zig
536 src/arch/riscv64/bits.zig
537 src/arch/riscv64/CodeGen.zig535 src/arch/riscv64/CodeGen.zig
538 src/arch/riscv64/Emit.zig536 src/arch/riscv64/Emit.zig
539 src/arch/riscv64/encoding.zig
540 src/arch/riscv64/Lower.zig537 src/arch/riscv64/Lower.zig
541 src/arch/riscv64/Mir.zig538 src/arch/riscv64/Mir.zig
539 src/arch/riscv64/abi.zig
540 src/arch/riscv64/bits.zig
541 src/arch/riscv64/encoding.zig
542 src/arch/riscv64/mnem.zig542 src/arch/riscv64/mnem.zig
543 src/arch/sparc64/CodeGen.zig543 src/arch/sparc64/CodeGen.zig
544 src/arch/sparc64/Emit.zig544 src/arch/sparc64/Emit.zig
...@@ -617,6 +617,7 @@ set(ZIG_STAGE2_SOURCES...@@ -617,6 +617,7 @@ set(ZIG_STAGE2_SOURCES
617 src/link/MachO/Object.zig617 src/link/MachO/Object.zig
618 src/link/MachO/Relocation.zig618 src/link/MachO/Relocation.zig
619 src/link/MachO/Symbol.zig619 src/link/MachO/Symbol.zig
620 src/link/MachO/Thunk.zig
620 src/link/MachO/UnwindInfo.zig621 src/link/MachO/UnwindInfo.zig
621 src/link/MachO/ZigObject.zig622 src/link/MachO/ZigObject.zig
622 src/link/MachO/dead_strip.zig623 src/link/MachO/dead_strip.zig
...@@ -630,7 +631,6 @@ set(ZIG_STAGE2_SOURCES...@@ -630,7 +631,6 @@ set(ZIG_STAGE2_SOURCES
630 src/link/MachO/load_commands.zig631 src/link/MachO/load_commands.zig
631 src/link/MachO/relocatable.zig632 src/link/MachO/relocatable.zig
632 src/link/MachO/synthetic.zig633 src/link/MachO/synthetic.zig
633 src/link/MachO/Thunk.zig
634 src/link/MachO/uuid.zig634 src/link/MachO/uuid.zig
635 src/link/NvPtx.zig635 src/link/NvPtx.zig
636 src/link/Plan9.zig636 src/link/Plan9.zig
...@@ -668,6 +668,9 @@ set(ZIG_STAGE2_SOURCES...@@ -668,6 +668,9 @@ set(ZIG_STAGE2_SOURCES
668 src/target.zig668 src/target.zig
669 src/tracy.zig669 src/tracy.zig
670 src/translate_c.zig670 src/translate_c.zig
671 src/translate_c/Tokenizer.zig
672 src/translate_c/aro.zig
673 src/translate_c/ast.zig
671 src/wasi_libc.zig674 src/wasi_libc.zig
672)675)
673676
...@@ -857,10 +860,8 @@ set(BUILD_ZIG2_ARGS...@@ -857,10 +860,8 @@ set(BUILD_ZIG2_ARGS
857 -femit-bin="${ZIG2_C_SOURCE}"860 -femit-bin="${ZIG2_C_SOURCE}"
858 -target "${ZIG_HOST_TARGET_TRIPLE}"861 -target "${ZIG_HOST_TARGET_TRIPLE}"
859 --dep "build_options"862 --dep "build_options"
860 --dep "aro"
861 "-Mroot=src/main.zig"863 "-Mroot=src/main.zig"
862 "-Mbuild_options=${ZIG_CONFIG_ZIG_OUT}"864 "-Mbuild_options=${ZIG_CONFIG_ZIG_OUT}"
863 "-Maro=lib/compiler/aro/aro.zig"
864)865)
865866
866add_custom_command(867add_custom_command(
build.zig-12
...@@ -668,18 +668,6 @@ fn addCompilerStep(b: *std.Build, options: AddCompilerStepOptions) *std.Build.St...@@ -668,18 +668,6 @@ fn addCompilerStep(b: *std.Build, options: AddCompilerStepOptions) *std.Build.St
668 .valgrind = options.valgrind,668 .valgrind = options.valgrind,
669 });669 });
670670
671 const aro_mod = b.createModule(.{
672 .root_source_file = b.path("lib/compiler/aro/aro.zig"),
673 });
674
675 const aro_translate_c_mod = b.createModule(.{
676 .root_source_file = b.path("lib/compiler/aro_translate_c.zig"),
677 });
678
679 aro_translate_c_mod.addImport("aro", aro_mod);
680 compiler_mod.addImport("aro", aro_mod);
681 compiler_mod.addImport("aro_translate_c", aro_translate_c_mod);
682
683 const exe = b.addExecutable(.{671 const exe = b.addExecutable(.{
684 .name = "zig",672 .name = "zig",
685 .max_rss = 7_800_000_000,673 .max_rss = 7_800_000_000,
lib/compiler/aro/README.md deleted-26
...@@ -1,26 +0,0 @@
1<img src="https://aro.vexu.eu/aro-logo.svg" alt="Aro" width="120px"/>
2
3# Aro
4
5A C compiler with the goal of providing fast compilation and low memory usage with good diagnostics.
6
7Aro is included as an alternative C frontend in the [Zig compiler](https://github.com/ziglang/zig)
8for `translate-c` and eventually compiling C files by translating them to Zig first.
9Aro is developed in https://github.com/Vexu/arocc and the Zig dependency is
10updated from there when needed.
11
12Currently most of standard C is supported up to C23 and as are many of the common
13extensions from GNU, MSVC, and Clang
14
15Basic code generation is supported for x86-64 linux and can produce a valid hello world:
16```sh-session
17$ cat hello.c
18extern int printf(const char *restrict fmt, ...);
19int main(void) {
20 printf("Hello, world!\n");
21 return 0;
22}
23$ zig build && ./zig-out/bin/arocc hello.c -o hello
24$ ./hello
25Hello, world!
26```
lib/compiler/aro/aro.zig deleted-39
...@@ -1,39 +0,0 @@
1pub const CodeGen = @import("aro/CodeGen.zig");
2pub const Compilation = @import("aro/Compilation.zig");
3pub const Diagnostics = @import("aro/Diagnostics.zig");
4pub const Driver = @import("aro/Driver.zig");
5pub const Parser = @import("aro/Parser.zig");
6pub const Preprocessor = @import("aro/Preprocessor.zig");
7pub const Source = @import("aro/Source.zig");
8pub const Tokenizer = @import("aro/Tokenizer.zig");
9pub const Toolchain = @import("aro/Toolchain.zig");
10pub const Tree = @import("aro/Tree.zig");
11pub const Type = @import("aro/Type.zig");
12pub const TypeMapper = @import("aro/StringInterner.zig").TypeMapper;
13pub const target_util = @import("aro/target.zig");
14pub const Value = @import("aro/Value.zig");
15
16const backend = @import("backend.zig");
17pub const Interner = backend.Interner;
18pub const Ir = backend.Ir;
19pub const Object = backend.Object;
20pub const CallingConvention = backend.CallingConvention;
21
22pub const version_str = backend.version_str;
23pub const version = backend.version;
24
25test {
26 _ = @import("aro/annex_g.zig");
27 _ = @import("aro/Builtins.zig");
28 _ = @import("aro/char_info.zig");
29 _ = @import("aro/Compilation.zig");
30 _ = @import("aro/Driver/Distro.zig");
31 _ = @import("aro/Driver/Filesystem.zig");
32 _ = @import("aro/Driver/GCCVersion.zig");
33 _ = @import("aro/InitList.zig");
34 _ = @import("aro/Preprocessor.zig");
35 _ = @import("aro/target.zig");
36 _ = @import("aro/Tokenizer.zig");
37 _ = @import("aro/toolchains/Linux.zig");
38 _ = @import("aro/Value.zig");
39}
lib/compiler/aro/aro/Attribute.zig deleted-1120
...@@ -1,1120 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const ZigType = std.builtin.Type;
4const CallingConvention = @import("../backend.zig").CallingConvention;
5const Compilation = @import("Compilation.zig");
6const Diagnostics = @import("Diagnostics.zig");
7const Parser = @import("Parser.zig");
8const Tree = @import("Tree.zig");
9const NodeIndex = Tree.NodeIndex;
10const TokenIndex = Tree.TokenIndex;
11const Type = @import("Type.zig");
12const Value = @import("Value.zig");
13
14const Attribute = @This();
15
16tag: Tag,
17syntax: Syntax,
18args: Arguments,
19
20pub const Syntax = enum {
21 c23,
22 declspec,
23 gnu,
24 keyword,
25};
26
27pub const Kind = enum {
28 c23,
29 declspec,
30 gnu,
31
32 pub fn toSyntax(kind: Kind) Syntax {
33 return switch (kind) {
34 .c23 => .c23,
35 .declspec => .declspec,
36 .gnu => .gnu,
37 };
38 }
39};
40
41pub const Iterator = struct {
42 source: union(enum) {
43 ty: Type,
44 slice: []const Attribute,
45 },
46 index: usize,
47
48 pub fn initSlice(slice: ?[]const Attribute) Iterator {
49 return .{ .source = .{ .slice = slice orelse &.{} }, .index = 0 };
50 }
51
52 pub fn initType(ty: Type) Iterator {
53 return .{ .source = .{ .ty = ty }, .index = 0 };
54 }
55
56 /// returns the next attribute as well as its index within the slice or current type
57 /// The index can be used to determine when a nested type has been recursed into
58 pub fn next(self: *Iterator) ?struct { Attribute, usize } {
59 switch (self.source) {
60 .slice => |slice| {
61 if (self.index < slice.len) {
62 defer self.index += 1;
63 return .{ slice[self.index], self.index };
64 }
65 },
66 .ty => |ty| {
67 switch (ty.specifier) {
68 .typeof_type => {
69 self.* = .{ .source = .{ .ty = ty.data.sub_type.* }, .index = 0 };
70 return self.next();
71 },
72 .typeof_expr => {
73 self.* = .{ .source = .{ .ty = ty.data.expr.ty }, .index = 0 };
74 return self.next();
75 },
76 .attributed => {
77 if (self.index < ty.data.attributed.attributes.len) {
78 defer self.index += 1;
79 return .{ ty.data.attributed.attributes[self.index], self.index };
80 }
81 self.* = .{ .source = .{ .ty = ty.data.attributed.base }, .index = 0 };
82 return self.next();
83 },
84 else => {},
85 }
86 },
87 }
88 return null;
89 }
90};
91
92pub const ArgumentType = enum {
93 string,
94 identifier,
95 int,
96 alignment,
97 float,
98 complex_float,
99 expression,
100 nullptr_t,
101
102 pub fn toString(self: ArgumentType) []const u8 {
103 return switch (self) {
104 .string => "a string",
105 .identifier => "an identifier",
106 .int, .alignment => "an integer constant",
107 .nullptr_t => "nullptr",
108 .float => "a floating point number",
109 .complex_float => "a complex floating point number",
110 .expression => "an expression",
111 };
112 }
113};
114
115/// number of required arguments
116pub fn requiredArgCount(attr: Tag) u32 {
117 switch (attr) {
118 inline else => |tag| {
119 comptime var needed = 0;
120 comptime {
121 const fields = @typeInfo(@field(attributes, @tagName(tag))).@"struct".fields;
122 for (fields) |arg_field| {
123 if (!mem.eql(u8, arg_field.name, "__name_tok") and @typeInfo(arg_field.type) != .optional) needed += 1;
124 }
125 }
126 return needed;
127 },
128 }
129}
130
131/// maximum number of args that can be passed
132pub fn maxArgCount(attr: Tag) u32 {
133 switch (attr) {
134 inline else => |tag| {
135 comptime var max = 0;
136 comptime {
137 const fields = @typeInfo(@field(attributes, @tagName(tag))).@"struct".fields;
138 for (fields) |arg_field| {
139 if (!mem.eql(u8, arg_field.name, "__name_tok")) max += 1;
140 }
141 }
142 return max;
143 },
144 }
145}
146
147fn UnwrapOptional(comptime T: type) type {
148 return switch (@typeInfo(T)) {
149 .optional => |optional| optional.child,
150 else => T,
151 };
152}
153
154pub const Formatting = struct {
155 /// The quote char (single or double) to use when printing identifiers/strings corresponding
156 /// to the enum in the first field of the `attr`. Identifier enums use single quotes, string enums
157 /// use double quotes
158 fn quoteChar(attr: Tag) []const u8 {
159 switch (attr) {
160 .calling_convention => unreachable,
161 inline else => |tag| {
162 const fields = @typeInfo(@field(attributes, @tagName(tag))).@"struct".fields;
163
164 if (fields.len == 0) unreachable;
165 const Unwrapped = UnwrapOptional(fields[0].type);
166 if (@typeInfo(Unwrapped) != .@"enum") unreachable;
167
168 return if (Unwrapped.opts.enum_kind == .identifier) "'" else "\"";
169 },
170 }
171 }
172
173 /// returns a comma-separated string of quoted enum values, representing the valid
174 /// choices for the string or identifier enum of the first field of the `attr`.
175 pub fn choices(attr: Tag) []const u8 {
176 switch (attr) {
177 .calling_convention => unreachable,
178 inline else => |tag| {
179 const fields = @typeInfo(@field(attributes, @tagName(tag))).@"struct".fields;
180
181 if (fields.len == 0) unreachable;
182 const Unwrapped = UnwrapOptional(fields[0].type);
183 if (@typeInfo(Unwrapped) != .@"enum") unreachable;
184
185 const enum_fields = @typeInfo(Unwrapped).@"enum".fields;
186 const quote = comptime quoteChar(@enumFromInt(@intFromEnum(tag)));
187 comptime var values: []const u8 = quote ++ enum_fields[0].name ++ quote;
188 inline for (enum_fields[1..]) |enum_field| {
189 values = values ++ ", ";
190 values = values ++ quote ++ enum_field.name ++ quote;
191 }
192 return values;
193 },
194 }
195 }
196};
197
198/// Checks if the first argument (if it exists) is an identifier enum
199pub fn wantsIdentEnum(attr: Tag) bool {
200 switch (attr) {
201 .calling_convention => return false,
202 inline else => |tag| {
203 const fields = @typeInfo(@field(attributes, @tagName(tag))).@"struct".fields;
204
205 if (fields.len == 0) return false;
206 const Unwrapped = UnwrapOptional(fields[0].type);
207 if (@typeInfo(Unwrapped) != .@"enum") return false;
208
209 return Unwrapped.opts.enum_kind == .identifier;
210 },
211 }
212}
213
214pub fn diagnoseIdent(attr: Tag, arguments: *Arguments, ident: []const u8) ?Diagnostics.Message {
215 switch (attr) {
216 inline else => |tag| {
217 const fields = @typeInfo(@field(attributes, @tagName(tag))).@"struct".fields;
218 if (fields.len == 0) unreachable;
219 const Unwrapped = UnwrapOptional(fields[0].type);
220 if (@typeInfo(Unwrapped) != .@"enum") unreachable;
221 if (std.meta.stringToEnum(Unwrapped, normalize(ident))) |enum_val| {
222 @field(@field(arguments, @tagName(tag)), fields[0].name) = enum_val;
223 return null;
224 }
225 return Diagnostics.Message{
226 .tag = .unknown_attr_enum,
227 .extra = .{ .attr_enum = .{ .tag = attr } },
228 };
229 },
230 }
231}
232
233pub fn wantsAlignment(attr: Tag, idx: usize) bool {
234 switch (attr) {
235 inline else => |tag| {
236 const fields = @typeInfo(@field(attributes, @tagName(tag))).@"struct".fields;
237 if (fields.len == 0) return false;
238
239 return switch (idx) {
240 inline 0...fields.len - 1 => |i| UnwrapOptional(fields[i].type) == Alignment,
241 else => false,
242 };
243 },
244 }
245}
246
247pub fn diagnoseAlignment(attr: Tag, arguments: *Arguments, arg_idx: u32, res: Parser.Result, p: *Parser) !?Diagnostics.Message {
248 switch (attr) {
249 inline else => |tag| {
250 const arg_fields = @typeInfo(@field(attributes, @tagName(tag))).@"struct".fields;
251 if (arg_fields.len == 0) unreachable;
252
253 switch (arg_idx) {
254 inline 0...arg_fields.len - 1 => |arg_i| {
255 if (UnwrapOptional(arg_fields[arg_i].type) != Alignment) unreachable;
256
257 if (!res.val.is(.int, p.comp)) return Diagnostics.Message{ .tag = .alignas_unavailable };
258 if (res.val.compare(.lt, Value.zero, p.comp)) {
259 return Diagnostics.Message{ .tag = .negative_alignment, .extra = .{ .str = try res.str(p) } };
260 }
261 const requested = res.val.toInt(u29, p.comp) orelse {
262 return Diagnostics.Message{ .tag = .maximum_alignment, .extra = .{ .str = try res.str(p) } };
263 };
264 if (!std.mem.isValidAlign(requested)) return Diagnostics.Message{ .tag = .non_pow2_align };
265
266 @field(@field(arguments, @tagName(tag)), arg_fields[arg_i].name) = Alignment{ .requested = requested };
267 return null;
268 },
269 else => unreachable,
270 }
271 },
272 }
273}
274
275fn diagnoseField(
276 comptime decl: ZigType.Declaration,
277 comptime field: ZigType.StructField,
278 comptime Wanted: type,
279 arguments: *Arguments,
280 res: Parser.Result,
281 node: Tree.Node,
282 p: *Parser,
283) !?Diagnostics.Message {
284 if (res.val.opt_ref == .none) {
285 if (Wanted == Identifier and node.tag == .decl_ref_expr) {
286 @field(@field(arguments, decl.name), field.name) = Identifier{ .tok = node.data.decl_ref };
287 return null;
288 }
289 return invalidArgMsg(Wanted, .expression);
290 }
291 const key = p.comp.interner.get(res.val.ref());
292 switch (key) {
293 .int => {
294 if (@typeInfo(Wanted) == .int) {
295 @field(@field(arguments, decl.name), field.name) = res.val.toInt(Wanted, p.comp) orelse return .{
296 .tag = .attribute_int_out_of_range,
297 .extra = .{ .str = try res.str(p) },
298 };
299 return null;
300 }
301 },
302 .bytes => |bytes| {
303 if (Wanted == Value) {
304 if (node.tag != .string_literal_expr or (!node.ty.elemType().is(.char) and !node.ty.elemType().is(.uchar))) {
305 return .{
306 .tag = .attribute_requires_string,
307 .extra = .{ .str = decl.name },
308 };
309 }
310 @field(@field(arguments, decl.name), field.name) = try p.removeNull(res.val);
311 return null;
312 } else if (@typeInfo(Wanted) == .@"enum" and @hasDecl(Wanted, "opts") and Wanted.opts.enum_kind == .string) {
313 const str = bytes[0 .. bytes.len - 1];
314 if (std.meta.stringToEnum(Wanted, str)) |enum_val| {
315 @field(@field(arguments, decl.name), field.name) = enum_val;
316 return null;
317 } else {
318 return .{
319 .tag = .unknown_attr_enum,
320 .extra = .{ .attr_enum = .{ .tag = std.meta.stringToEnum(Tag, decl.name).? } },
321 };
322 }
323 }
324 },
325 else => {},
326 }
327 return invalidArgMsg(Wanted, switch (key) {
328 .int => .int,
329 .bytes => .string,
330 .float => .float,
331 .complex => .complex_float,
332 .null => .nullptr_t,
333 .int_ty,
334 .float_ty,
335 .complex_ty,
336 .ptr_ty,
337 .noreturn_ty,
338 .void_ty,
339 .func_ty,
340 .array_ty,
341 .vector_ty,
342 .record_ty,
343 => unreachable,
344 });
345}
346
347fn invalidArgMsg(comptime Expected: type, actual: ArgumentType) Diagnostics.Message {
348 return .{
349 .tag = .attribute_arg_invalid,
350 .extra = .{ .attr_arg_type = .{ .expected = switch (Expected) {
351 Value => .string,
352 Identifier => .identifier,
353 u32 => .int,
354 Alignment => .alignment,
355 CallingConvention => .identifier,
356 else => switch (@typeInfo(Expected)) {
357 .@"enum" => if (Expected.opts.enum_kind == .string) .string else .identifier,
358 else => unreachable,
359 },
360 }, .actual = actual } },
361 };
362}
363
364pub fn diagnose(attr: Tag, arguments: *Arguments, arg_idx: u32, res: Parser.Result, node: Tree.Node, p: *Parser) !?Diagnostics.Message {
365 switch (attr) {
366 inline else => |tag| {
367 const decl = @typeInfo(attributes).@"struct".decls[@intFromEnum(tag)];
368 const max_arg_count = comptime maxArgCount(tag);
369 if (arg_idx >= max_arg_count) return Diagnostics.Message{
370 .tag = .attribute_too_many_args,
371 .extra = .{ .attr_arg_count = .{ .attribute = attr, .expected = max_arg_count } },
372 };
373 const arg_fields = @typeInfo(@field(attributes, decl.name)).@"struct".fields;
374 switch (arg_idx) {
375 inline 0...arg_fields.len - 1 => |arg_i| {
376 return diagnoseField(decl, arg_fields[arg_i], UnwrapOptional(arg_fields[arg_i].type), arguments, res, node, p);
377 },
378 else => unreachable,
379 }
380 },
381 }
382}
383
384const EnumTypes = enum {
385 string,
386 identifier,
387};
388pub const Alignment = struct {
389 node: NodeIndex = .none,
390 requested: u29,
391};
392pub const Identifier = struct {
393 tok: TokenIndex = 0,
394};
395
396const attributes = struct {
397 pub const access = struct {
398 access_mode: enum {
399 read_only,
400 read_write,
401 write_only,
402 none,
403
404 const opts = struct {
405 const enum_kind = .identifier;
406 };
407 },
408 ref_index: u32,
409 size_index: ?u32 = null,
410 };
411 pub const alias = struct {
412 alias: Value,
413 };
414 pub const aligned = struct {
415 alignment: ?Alignment = null,
416 __name_tok: TokenIndex,
417 };
418 pub const alloc_align = struct {
419 position: u32,
420 };
421 pub const alloc_size = struct {
422 position_1: u32,
423 position_2: ?u32 = null,
424 };
425 pub const allocate = struct {
426 segname: Value,
427 };
428 pub const allocator = struct {};
429 pub const always_inline = struct {};
430 pub const appdomain = struct {};
431 pub const artificial = struct {};
432 pub const assume_aligned = struct {
433 alignment: Alignment,
434 offset: ?u32 = null,
435 };
436 pub const cleanup = struct {
437 function: Identifier,
438 };
439 pub const code_seg = struct {
440 segname: Value,
441 };
442 pub const cold = struct {};
443 pub const common = struct {};
444 pub const @"const" = struct {};
445 pub const constructor = struct {
446 priority: ?u32 = null,
447 };
448 pub const copy = struct {
449 function: Identifier,
450 };
451 pub const deprecated = struct {
452 msg: ?Value = null,
453 __name_tok: TokenIndex,
454 };
455 pub const designated_init = struct {};
456 pub const destructor = struct {
457 priority: ?u32 = null,
458 };
459 pub const dllexport = struct {};
460 pub const dllimport = struct {};
461 pub const @"error" = struct {
462 msg: Value,
463 __name_tok: TokenIndex,
464 };
465 pub const externally_visible = struct {};
466 pub const fallthrough = struct {};
467 pub const flatten = struct {};
468 pub const format = struct {
469 archetype: enum {
470 printf,
471 scanf,
472 strftime,
473 strfmon,
474
475 const opts = struct {
476 const enum_kind = .identifier;
477 };
478 },
479 string_index: u32,
480 first_to_check: u32,
481 };
482 pub const format_arg = struct {
483 string_index: u32,
484 };
485 pub const gnu_inline = struct {};
486 pub const hot = struct {};
487 pub const ifunc = struct {
488 resolver: Value,
489 };
490 pub const interrupt = struct {};
491 pub const interrupt_handler = struct {};
492 pub const jitintrinsic = struct {};
493 pub const leaf = struct {};
494 pub const malloc = struct {};
495 pub const may_alias = struct {};
496 pub const mode = struct {
497 mode: enum {
498 // zig fmt: off
499 byte, word, pointer,
500 BI, QI, HI,
501 PSI, SI, PDI,
502 DI, TI, OI,
503 XI, QF, HF,
504 TQF, SF, DF,
505 XF, SD, DD,
506 TD, TF, QQ,
507 HQ, SQ, DQ,
508 TQ, UQQ, UHQ,
509 USQ, UDQ, UTQ,
510 HA, SA, DA,
511 TA, UHA, USA,
512 UDA, UTA, CC,
513 BLK, VOID, QC,
514 HC, SC, DC,
515 XC, TC, CQI,
516 CHI, CSI, CDI,
517 CTI, COI, CPSI,
518 BND32, BND64,
519 // zig fmt: on
520
521 const opts = struct {
522 const enum_kind = .identifier;
523 };
524 },
525 };
526 pub const naked = struct {};
527 pub const no_address_safety_analysis = struct {};
528 pub const no_icf = struct {};
529 pub const no_instrument_function = struct {};
530 pub const no_profile_instrument_function = struct {};
531 pub const no_reorder = struct {};
532 pub const no_sanitize = struct {
533 /// Todo: represent args as union?
534 alignment: Value,
535 object_size: ?Value = null,
536 };
537 pub const no_sanitize_address = struct {};
538 pub const no_sanitize_coverage = struct {};
539 pub const no_sanitize_thread = struct {};
540 pub const no_sanitize_undefined = struct {};
541 pub const no_split_stack = struct {};
542 pub const no_stack_limit = struct {};
543 pub const no_stack_protector = struct {};
544 pub const @"noalias" = struct {};
545 pub const noclone = struct {};
546 pub const nocommon = struct {};
547 pub const nodiscard = struct {};
548 pub const noinit = struct {};
549 pub const @"noinline" = struct {};
550 pub const noipa = struct {};
551 // TODO: arbitrary number of arguments
552 // const nonnull = struct {
553 // // arg_index: []const u32,
554 // };
555 // };
556 pub const nonstring = struct {};
557 pub const noplt = struct {};
558 pub const @"noreturn" = struct {};
559 // TODO: union args ?
560 // const optimize = struct {
561 // // optimize, // u32 | []const u8 -- optimize?
562 // };
563 // };
564 pub const @"packed" = struct {};
565 pub const patchable_function_entry = struct {};
566 pub const persistent = struct {};
567 pub const process = struct {};
568 pub const pure = struct {};
569 pub const reproducible = struct {};
570 pub const restrict = struct {};
571 pub const retain = struct {};
572 pub const returns_nonnull = struct {};
573 pub const returns_twice = struct {};
574 pub const safebuffers = struct {};
575 pub const scalar_storage_order = struct {
576 order: enum {
577 @"little-endian",
578 @"big-endian",
579
580 const opts = struct {
581 const enum_kind = .string;
582 };
583 },
584 };
585 pub const section = struct {
586 name: Value,
587 };
588 pub const selectany = struct {};
589 pub const sentinel = struct {
590 position: ?u32 = null,
591 };
592 pub const simd = struct {
593 mask: ?enum {
594 notinbranch,
595 inbranch,
596
597 const opts = struct {
598 const enum_kind = .string;
599 };
600 } = null,
601 };
602 pub const spectre = struct {
603 arg: enum {
604 nomitigation,
605
606 const opts = struct {
607 const enum_kind = .identifier;
608 };
609 },
610 };
611 pub const stack_protect = struct {};
612 pub const symver = struct {
613 version: Value, // TODO: validate format "name2@nodename"
614
615 };
616 pub const target = struct {
617 options: Value, // TODO: multiple arguments
618
619 };
620 pub const target_clones = struct {
621 options: Value, // TODO: multiple arguments
622
623 };
624 pub const thread = struct {};
625 pub const tls_model = struct {
626 model: enum {
627 @"global-dynamic",
628 @"local-dynamic",
629 @"initial-exec",
630 @"local-exec",
631
632 const opts = struct {
633 const enum_kind = .string;
634 };
635 },
636 };
637 pub const transparent_union = struct {};
638 pub const unavailable = struct {
639 msg: ?Value = null,
640 __name_tok: TokenIndex,
641 };
642 pub const uninitialized = struct {};
643 pub const unsequenced = struct {};
644 pub const unused = struct {};
645 pub const used = struct {};
646 pub const uuid = struct {
647 uuid: Value,
648 };
649 pub const vector_size = struct {
650 bytes: u32, // TODO: validate "The bytes argument must be a positive power-of-two multiple of the base type size"
651
652 };
653 pub const visibility = struct {
654 visibility_type: enum {
655 default,
656 hidden,
657 internal,
658 protected,
659
660 const opts = struct {
661 const enum_kind = .string;
662 };
663 },
664 };
665 pub const warn_if_not_aligned = struct {
666 alignment: Alignment,
667 };
668 pub const warn_unused_result = struct {};
669 pub const warning = struct {
670 msg: Value,
671 __name_tok: TokenIndex,
672 };
673 pub const weak = struct {};
674 pub const weakref = struct {
675 target: ?Value = null,
676 };
677 pub const zero_call_used_regs = struct {
678 choice: enum {
679 skip,
680 used,
681 @"used-gpr",
682 @"used-arg",
683 @"used-gpr-arg",
684 all,
685 @"all-gpr",
686 @"all-arg",
687 @"all-gpr-arg",
688
689 const opts = struct {
690 const enum_kind = .string;
691 };
692 },
693 };
694 pub const asm_label = struct {
695 name: Value,
696 };
697 pub const calling_convention = struct {
698 cc: CallingConvention,
699 };
700};
701
702pub const Tag = std.meta.DeclEnum(attributes);
703
704pub const Arguments = blk: {
705 const decls = @typeInfo(attributes).@"struct".decls;
706 var union_fields: [decls.len]ZigType.UnionField = undefined;
707 for (decls, &union_fields) |decl, *field| {
708 field.* = .{
709 .name = decl.name,
710 .type = @field(attributes, decl.name),
711 .alignment = 0,
712 };
713 }
714
715 break :blk @Type(.{
716 .@"union" = .{
717 .layout = .auto,
718 .tag_type = null,
719 .fields = &union_fields,
720 .decls = &.{},
721 },
722 });
723};
724
725pub fn ArgumentsForTag(comptime tag: Tag) type {
726 const decl = @typeInfo(attributes).@"struct".decls[@intFromEnum(tag)];
727 return @field(attributes, decl.name);
728}
729
730pub fn initArguments(tag: Tag, name_tok: TokenIndex) Arguments {
731 switch (tag) {
732 inline else => |arg_tag| {
733 const union_element = @field(attributes, @tagName(arg_tag));
734 const init = std.mem.zeroInit(union_element, .{});
735 var args = @unionInit(Arguments, @tagName(arg_tag), init);
736 if (@hasField(@field(attributes, @tagName(arg_tag)), "__name_tok")) {
737 @field(args, @tagName(arg_tag)).__name_tok = name_tok;
738 }
739 return args;
740 },
741 }
742}
743
744pub fn fromString(kind: Kind, namespace: ?[]const u8, name: []const u8) ?Tag {
745 const Properties = struct {
746 tag: Tag,
747 gnu: bool = false,
748 declspec: bool = false,
749 c23: bool = false,
750 };
751 const attribute_names = @import("Attribute/names.zig").with(Properties);
752
753 const normalized = normalize(name);
754 const actual_kind: Kind = if (namespace) |ns| blk: {
755 const normalized_ns = normalize(ns);
756 if (mem.eql(u8, normalized_ns, "gnu")) {
757 break :blk .gnu;
758 }
759 return null;
760 } else kind;
761
762 const tag_and_opts = attribute_names.fromName(normalized) orelse return null;
763 switch (actual_kind) {
764 inline else => |tag| {
765 if (@field(tag_and_opts.properties, @tagName(tag)))
766 return tag_and_opts.properties.tag;
767 },
768 }
769 return null;
770}
771
772pub fn normalize(name: []const u8) []const u8 {
773 if (name.len >= 4 and mem.startsWith(u8, name, "__") and mem.endsWith(u8, name, "__")) {
774 return name[2 .. name.len - 2];
775 }
776 return name;
777}
778
779fn ignoredAttrErr(p: *Parser, tok: TokenIndex, attr: Attribute.Tag, context: []const u8) !void {
780 const strings_top = p.strings.items.len;
781 defer p.strings.items.len = strings_top;
782
783 try p.strings.writer().print("attribute '{s}' ignored on {s}", .{ @tagName(attr), context });
784 const str = try p.comp.diagnostics.arena.allocator().dupe(u8, p.strings.items[strings_top..]);
785 try p.errStr(.ignored_attribute, tok, str);
786}
787
788pub const applyParameterAttributes = applyVariableAttributes;
789pub fn applyVariableAttributes(p: *Parser, ty: Type, attr_buf_start: usize, tag: ?Diagnostics.Tag) !Type {
790 const attrs = p.attr_buf.items(.attr)[attr_buf_start..];
791 const toks = p.attr_buf.items(.tok)[attr_buf_start..];
792 p.attr_application_buf.items.len = 0;
793 var base_ty = ty;
794 var common = false;
795 var nocommon = false;
796 for (attrs, toks) |attr, tok| switch (attr.tag) {
797 // zig fmt: off
798 .alias, .may_alias, .deprecated, .unavailable, .unused, .warn_if_not_aligned, .weak, .used,
799 .noinit, .retain, .persistent, .section, .mode, .asm_label,
800 => try p.attr_application_buf.append(p.gpa, attr),
801 // zig fmt: on
802 .common => if (nocommon) {
803 try p.errTok(.ignore_common, tok);
804 } else {
805 try p.attr_application_buf.append(p.gpa, attr);
806 common = true;
807 },
808 .nocommon => if (common) {
809 try p.errTok(.ignore_nocommon, tok);
810 } else {
811 try p.attr_application_buf.append(p.gpa, attr);
812 nocommon = true;
813 },
814 .vector_size => try attr.applyVectorSize(p, tok, &base_ty),
815 .aligned => try attr.applyAligned(p, base_ty, tag),
816 .nonstring => if (!base_ty.isArray() or !(base_ty.is(.char) or base_ty.is(.uchar) or base_ty.is(.schar))) {
817 try p.errStr(.non_string_ignored, tok, try p.typeStr(ty));
818 } else {
819 try p.attr_application_buf.append(p.gpa, attr);
820 },
821 .uninitialized => if (p.func.ty == null) {
822 try p.errStr(.local_variable_attribute, tok, "uninitialized");
823 } else {
824 try p.attr_application_buf.append(p.gpa, attr);
825 },
826 .cleanup => if (p.func.ty == null) {
827 try p.errStr(.local_variable_attribute, tok, "cleanup");
828 } else {
829 try p.attr_application_buf.append(p.gpa, attr);
830 },
831 .alloc_size,
832 .copy,
833 .tls_model,
834 .visibility,
835 => |t| try p.errExtra(.attribute_todo, tok, .{ .attribute_todo = .{ .tag = t, .kind = .variables } }),
836 else => try ignoredAttrErr(p, tok, attr.tag, "variables"),
837 };
838 return base_ty.withAttributes(p.arena, p.attr_application_buf.items);
839}
840
841pub fn applyFieldAttributes(p: *Parser, field_ty: *Type, attr_buf_start: usize) ![]const Attribute {
842 const attrs = p.attr_buf.items(.attr)[attr_buf_start..];
843 const toks = p.attr_buf.items(.tok)[attr_buf_start..];
844 p.attr_application_buf.items.len = 0;
845 for (attrs, toks) |attr, tok| switch (attr.tag) {
846 // zig fmt: off
847 .@"packed", .may_alias, .deprecated, .unavailable, .unused, .warn_if_not_aligned, .mode, .warn_unused_result, .nodiscard,
848 => try p.attr_application_buf.append(p.gpa, attr),
849 // zig fmt: on
850 .vector_size => try attr.applyVectorSize(p, tok, field_ty),
851 .aligned => try attr.applyAligned(p, field_ty.*, null),
852 else => try ignoredAttrErr(p, tok, attr.tag, "fields"),
853 };
854 if (p.attr_application_buf.items.len == 0) return &[0]Attribute{};
855 return p.arena.dupe(Attribute, p.attr_application_buf.items);
856}
857
858pub fn applyTypeAttributes(p: *Parser, ty: Type, attr_buf_start: usize, tag: ?Diagnostics.Tag) !Type {
859 const attrs = p.attr_buf.items(.attr)[attr_buf_start..];
860 const toks = p.attr_buf.items(.tok)[attr_buf_start..];
861 p.attr_application_buf.items.len = 0;
862 var base_ty = ty;
863 for (attrs, toks) |attr, tok| switch (attr.tag) {
864 // zig fmt: off
865 .@"packed", .may_alias, .deprecated, .unavailable, .unused, .warn_if_not_aligned, .mode,
866 => try p.attr_application_buf.append(p.gpa, attr),
867 // zig fmt: on
868 .transparent_union => try attr.applyTransparentUnion(p, tok, base_ty),
869 .vector_size => try attr.applyVectorSize(p, tok, &base_ty),
870 .aligned => try attr.applyAligned(p, base_ty, tag),
871 .designated_init => if (base_ty.is(.@"struct")) {
872 try p.attr_application_buf.append(p.gpa, attr);
873 } else {
874 try p.errTok(.designated_init_invalid, tok);
875 },
876 .alloc_size,
877 .copy,
878 .scalar_storage_order,
879 .nonstring,
880 => |t| try p.errExtra(.attribute_todo, tok, .{ .attribute_todo = .{ .tag = t, .kind = .types } }),
881 else => try ignoredAttrErr(p, tok, attr.tag, "types"),
882 };
883 return base_ty.withAttributes(p.arena, p.attr_application_buf.items);
884}
885
886pub fn applyFunctionAttributes(p: *Parser, ty: Type, attr_buf_start: usize) !Type {
887 const attrs = p.attr_buf.items(.attr)[attr_buf_start..];
888 const toks = p.attr_buf.items(.tok)[attr_buf_start..];
889 p.attr_application_buf.items.len = 0;
890 var base_ty = ty;
891 var hot = false;
892 var cold = false;
893 var @"noinline" = false;
894 var always_inline = false;
895 for (attrs, toks) |attr, tok| switch (attr.tag) {
896 // zig fmt: off
897 .noreturn, .unused, .used, .warning, .deprecated, .unavailable, .weak, .pure, .leaf,
898 .@"const", .warn_unused_result, .section, .returns_nonnull, .returns_twice, .@"error",
899 .externally_visible, .retain, .flatten, .gnu_inline, .alias, .asm_label, .nodiscard,
900 .reproducible, .unsequenced,
901 => try p.attr_application_buf.append(p.gpa, attr),
902 // zig fmt: on
903 .hot => if (cold) {
904 try p.errTok(.ignore_hot, tok);
905 } else {
906 try p.attr_application_buf.append(p.gpa, attr);
907 hot = true;
908 },
909 .cold => if (hot) {
910 try p.errTok(.ignore_cold, tok);
911 } else {
912 try p.attr_application_buf.append(p.gpa, attr);
913 cold = true;
914 },
915 .always_inline => if (@"noinline") {
916 try p.errTok(.ignore_always_inline, tok);
917 } else {
918 try p.attr_application_buf.append(p.gpa, attr);
919 always_inline = true;
920 },
921 .@"noinline" => if (always_inline) {
922 try p.errTok(.ignore_noinline, tok);
923 } else {
924 try p.attr_application_buf.append(p.gpa, attr);
925 @"noinline" = true;
926 },
927 .aligned => try attr.applyAligned(p, base_ty, null),
928 .format => try attr.applyFormat(p, base_ty),
929 .calling_convention => switch (attr.args.calling_convention.cc) {
930 .C => continue,
931 .stdcall, .thiscall => switch (p.comp.target.cpu.arch) {
932 .x86 => try p.attr_application_buf.append(p.gpa, attr),
933 else => try p.errStr(.callconv_not_supported, tok, p.tok_ids[tok].lexeme().?),
934 },
935 .vectorcall => switch (p.comp.target.cpu.arch) {
936 .x86, .aarch64, .aarch64_be => try p.attr_application_buf.append(p.gpa, attr),
937 else => try p.errStr(.callconv_not_supported, tok, p.tok_ids[tok].lexeme().?),
938 },
939 },
940 .malloc => {
941 if (base_ty.returnType().isPtr()) {
942 try p.attr_application_buf.append(p.gpa, attr);
943 } else {
944 try ignoredAttrErr(p, tok, attr.tag, "functions that do not return pointers");
945 }
946 },
947 .access,
948 .alloc_align,
949 .alloc_size,
950 .artificial,
951 .assume_aligned,
952 .constructor,
953 .copy,
954 .destructor,
955 .format_arg,
956 .ifunc,
957 .interrupt,
958 .interrupt_handler,
959 .no_address_safety_analysis,
960 .no_icf,
961 .no_instrument_function,
962 .no_profile_instrument_function,
963 .no_reorder,
964 .no_sanitize,
965 .no_sanitize_address,
966 .no_sanitize_coverage,
967 .no_sanitize_thread,
968 .no_sanitize_undefined,
969 .no_split_stack,
970 .no_stack_limit,
971 .no_stack_protector,
972 .noclone,
973 .noipa,
974 // .nonnull,
975 .noplt,
976 // .optimize,
977 .patchable_function_entry,
978 .sentinel,
979 .simd,
980 .stack_protect,
981 .symver,
982 .target,
983 .target_clones,
984 .visibility,
985 .weakref,
986 .zero_call_used_regs,
987 => |t| try p.errExtra(.attribute_todo, tok, .{ .attribute_todo = .{ .tag = t, .kind = .functions } }),
988 else => try ignoredAttrErr(p, tok, attr.tag, "functions"),
989 };
990 return ty.withAttributes(p.arena, p.attr_application_buf.items);
991}
992
993pub fn applyLabelAttributes(p: *Parser, ty: Type, attr_buf_start: usize) !Type {
994 const attrs = p.attr_buf.items(.attr)[attr_buf_start..];
995 const toks = p.attr_buf.items(.tok)[attr_buf_start..];
996 p.attr_application_buf.items.len = 0;
997 var hot = false;
998 var cold = false;
999 for (attrs, toks) |attr, tok| switch (attr.tag) {
1000 .unused => try p.attr_application_buf.append(p.gpa, attr),
1001 .hot => if (cold) {
1002 try p.errTok(.ignore_hot, tok);
1003 } else {
1004 try p.attr_application_buf.append(p.gpa, attr);
1005 hot = true;
1006 },
1007 .cold => if (hot) {
1008 try p.errTok(.ignore_cold, tok);
1009 } else {
1010 try p.attr_application_buf.append(p.gpa, attr);
1011 cold = true;
1012 },
1013 else => try ignoredAttrErr(p, tok, attr.tag, "labels"),
1014 };
1015 return ty.withAttributes(p.arena, p.attr_application_buf.items);
1016}
1017
1018pub fn applyStatementAttributes(p: *Parser, ty: Type, expr_start: TokenIndex, attr_buf_start: usize) !Type {
1019 const attrs = p.attr_buf.items(.attr)[attr_buf_start..];
1020 const toks = p.attr_buf.items(.tok)[attr_buf_start..];
1021 p.attr_application_buf.items.len = 0;
1022 for (attrs, toks) |attr, tok| switch (attr.tag) {
1023 .fallthrough => if (p.tok_ids[p.tok_i] != .keyword_case and p.tok_ids[p.tok_i] != .keyword_default) {
1024 // TODO: this condition is not completely correct; the last statement of a compound
1025 // statement is also valid if it precedes a switch label (so intervening '}' are ok,
1026 // but only if they close a compound statement)
1027 try p.errTok(.invalid_fallthrough, expr_start);
1028 } else {
1029 try p.attr_application_buf.append(p.gpa, attr);
1030 },
1031 else => try p.errStr(.cannot_apply_attribute_to_statement, tok, @tagName(attr.tag)),
1032 };
1033 return ty.withAttributes(p.arena, p.attr_application_buf.items);
1034}
1035
1036pub fn applyEnumeratorAttributes(p: *Parser, ty: Type, attr_buf_start: usize) !Type {
1037 const attrs = p.attr_buf.items(.attr)[attr_buf_start..];
1038 const toks = p.attr_buf.items(.tok)[attr_buf_start..];
1039 p.attr_application_buf.items.len = 0;
1040 for (attrs, toks) |attr, tok| switch (attr.tag) {
1041 .deprecated, .unavailable => try p.attr_application_buf.append(p.gpa, attr),
1042 else => try ignoredAttrErr(p, tok, attr.tag, "enums"),
1043 };
1044 return ty.withAttributes(p.arena, p.attr_application_buf.items);
1045}
1046
1047fn applyAligned(attr: Attribute, p: *Parser, ty: Type, tag: ?Diagnostics.Tag) !void {
1048 const base = ty.canonicalize(.standard);
1049 if (attr.args.aligned.alignment) |alignment| alignas: {
1050 if (attr.syntax != .keyword) break :alignas;
1051
1052 const align_tok = attr.args.aligned.__name_tok;
1053 if (tag) |t| try p.errTok(t, align_tok);
1054
1055 const default_align = base.alignof(p.comp);
1056 if (ty.isFunc()) {
1057 try p.errTok(.alignas_on_func, align_tok);
1058 } else if (alignment.requested < default_align) {
1059 try p.errExtra(.minimum_alignment, align_tok, .{ .unsigned = default_align });
1060 }
1061 }
1062 try p.attr_application_buf.append(p.gpa, attr);
1063}
1064
1065fn applyTransparentUnion(attr: Attribute, p: *Parser, tok: TokenIndex, ty: Type) !void {
1066 const union_ty = ty.get(.@"union") orelse {
1067 return p.errTok(.transparent_union_wrong_type, tok);
1068 };
1069 // TODO validate union defined at end
1070 if (union_ty.data.record.isIncomplete()) return;
1071 const fields = union_ty.data.record.fields;
1072 if (fields.len == 0) {
1073 return p.errTok(.transparent_union_one_field, tok);
1074 }
1075 const first_field_size = fields[0].ty.bitSizeof(p.comp).?;
1076 for (fields[1..]) |field| {
1077 const field_size = field.ty.bitSizeof(p.comp).?;
1078 if (field_size == first_field_size) continue;
1079 const mapper = p.comp.string_interner.getSlowTypeMapper();
1080 const str = try std.fmt.allocPrint(
1081 p.comp.diagnostics.arena.allocator(),
1082 "'{s}' ({d}",
1083 .{ mapper.lookup(field.name), field_size },
1084 );
1085 try p.errStr(.transparent_union_size, field.name_tok, str);
1086 return p.errExtra(.transparent_union_size_note, fields[0].name_tok, .{ .unsigned = first_field_size });
1087 }
1088
1089 try p.attr_application_buf.append(p.gpa, attr);
1090}
1091
1092fn applyVectorSize(attr: Attribute, p: *Parser, tok: TokenIndex, ty: *Type) !void {
1093 const base = ty.base();
1094 const is_enum = ty.is(.@"enum");
1095 if (!(ty.isInt() or ty.isFloat()) or !ty.isReal() or (is_enum and p.comp.langopts.emulate == .gcc)) {
1096 try p.errStr(.invalid_vec_elem_ty, tok, try p.typeStr(ty.*));
1097 return error.ParsingFailed;
1098 }
1099 if (is_enum) return;
1100
1101 const vec_bytes = attr.args.vector_size.bytes;
1102 const ty_size = ty.sizeof(p.comp).?;
1103 if (vec_bytes % ty_size != 0) {
1104 return p.errTok(.vec_size_not_multiple, tok);
1105 }
1106 const vec_size = vec_bytes / ty_size;
1107
1108 const arr_ty = try p.arena.create(Type.Array);
1109 arr_ty.* = .{ .elem = ty.*, .len = vec_size };
1110 base.* = .{
1111 .specifier = .vector,
1112 .data = .{ .array = arr_ty },
1113 };
1114}
1115
1116fn applyFormat(attr: Attribute, p: *Parser, ty: Type) !void {
1117 // TODO validate
1118 _ = ty;
1119 try p.attr_application_buf.append(p.gpa, attr);
1120}
lib/compiler/aro/aro/Attribute/names.zig deleted-1002
...@@ -1,1002 +0,0 @@
1//! Autogenerated by GenerateDef from src/aro/Attribute/names.def, do not edit
2// zig fmt: off
3
4const std = @import("std");
5
6pub fn with(comptime Properties: type) type {
7return struct {
8
9tag: Tag,
10properties: Properties,
11
12/// Integer starting at 0 derived from the unique index,
13/// corresponds with the data array index.
14pub const Tag = enum(u16) { _ };
15
16const Self = @This();
17
18pub fn fromName(name: []const u8) ?@This() {
19 const data_index = tagFromName(name) orelse return null;
20 return data[@intFromEnum(data_index)];
21}
22
23pub fn tagFromName(name: []const u8) ?Tag {
24 const unique_index = uniqueIndex(name) orelse return null;
25 return @enumFromInt(unique_index - 1);
26}
27
28pub fn fromTag(tag: Tag) @This() {
29 return data[@intFromEnum(tag)];
30}
31
32pub fn nameFromTagIntoBuf(tag: Tag, name_buf: []u8) []u8 {
33 std.debug.assert(name_buf.len >= longest_name);
34 const unique_index = @intFromEnum(tag) + 1;
35 return nameFromUniqueIndex(unique_index, name_buf);
36}
37
38pub fn nameFromTag(tag: Tag) NameBuf {
39 var name_buf: NameBuf = undefined;
40 const unique_index = @intFromEnum(tag) + 1;
41 const name = nameFromUniqueIndex(unique_index, &name_buf.buf);
42 name_buf.len = @intCast(name.len);
43 return name_buf;
44}
45
46pub const NameBuf = struct {
47 buf: [longest_name]u8 = undefined,
48 len: std.math.IntFittingRange(0, longest_name),
49
50 pub fn span(self: *const NameBuf) []const u8 {
51 return self.buf[0..self.len];
52 }
53};
54
55pub fn exists(name: []const u8) bool {
56 if (name.len < shortest_name or name.len > longest_name) return false;
57
58 var index: u16 = 0;
59 for (name) |c| {
60 index = findInList(dafsa[index].child_index, c) orelse return false;
61 }
62 return dafsa[index].end_of_word;
63}
64
65pub const shortest_name = 3;
66pub const longest_name = 30;
67
68/// Search siblings of `first_child_index` for the `char`
69/// If found, returns the index of the node within the `dafsa` array.
70/// Otherwise, returns `null`.
71pub fn findInList(first_child_index: u16, char: u8) ?u16 {
72 @setEvalBranchQuota(206);
73 var index = first_child_index;
74 while (true) {
75 if (dafsa[index].char == char) return index;
76 if (dafsa[index].end_of_list) return null;
77 index += 1;
78 }
79 unreachable;
80}
81
82/// Returns a unique (minimal perfect hash) index (starting at 1) for the `name`,
83/// or null if the name was not found.
84pub fn uniqueIndex(name: []const u8) ?u16 {
85 if (name.len < shortest_name or name.len > longest_name) return null;
86
87 var index: u16 = 0;
88 var node_index: u16 = 0;
89
90 for (name) |c| {
91 const child_index = findInList(dafsa[node_index].child_index, c) orelse return null;
92 var sibling_index = dafsa[node_index].child_index;
93 while (true) {
94 const sibling_c = dafsa[sibling_index].char;
95 std.debug.assert(sibling_c != 0);
96 if (sibling_c < c) {
97 index += dafsa[sibling_index].number;
98 }
99 if (dafsa[sibling_index].end_of_list) break;
100 sibling_index += 1;
101 }
102 node_index = child_index;
103 if (dafsa[node_index].end_of_word) index += 1;
104 }
105
106 if (!dafsa[node_index].end_of_word) return null;
107
108 return index;
109}
110
111/// Returns a slice of `buf` with the name associated with the given `index`.
112/// This function should only be called with an `index` that
113/// is already known to exist within the `dafsa`, e.g. an index
114/// returned from `uniqueIndex`.
115pub fn nameFromUniqueIndex(index: u16, buf: []u8) []u8 {
116 std.debug.assert(index >= 1 and index <= data.len);
117
118 var node_index: u16 = 0;
119 var count: u16 = index;
120 var fbs = std.io.fixedBufferStream(buf);
121 const w = fbs.writer();
122
123 while (true) {
124 var sibling_index = dafsa[node_index].child_index;
125 while (true) {
126 if (dafsa[sibling_index].number > 0 and dafsa[sibling_index].number < count) {
127 count -= dafsa[sibling_index].number;
128 } else {
129 w.writeByte(dafsa[sibling_index].char) catch unreachable;
130 node_index = sibling_index;
131 if (dafsa[node_index].end_of_word) {
132 count -= 1;
133 }
134 break;
135 }
136
137 if (dafsa[sibling_index].end_of_list) break;
138 sibling_index += 1;
139 }
140 if (count == 0) break;
141 }
142
143 return fbs.getWritten();
144}
145
146const Node = packed struct(u32) {
147 char: u8,
148 /// Nodes are numbered with "an integer which gives the number of words that
149 /// would be accepted by the automaton starting from that state." This numbering
150 /// allows calculating "a one-to-one correspondence between the integers 1 to L
151 /// (L is the number of words accepted by the automaton) and the words themselves."
152 ///
153 /// Essentially, this allows us to have a minimal perfect hashing scheme such that
154 /// it's possible to store & lookup the properties of each name using a separate array.
155 number: u8,
156 /// If true, this node is the end of a valid name.
157 /// Note: This does not necessarily mean that this node does not have child nodes.
158 end_of_word: bool,
159 /// If true, this node is the end of a sibling list.
160 /// If false, then (index + 1) will contain the next sibling.
161 end_of_list: bool,
162 /// Index of the first child of this node.
163 child_index: u14,
164};
165
166const dafsa = [_]Node{
167 .{ .char = 0, .end_of_word = false, .end_of_list = true, .number = 0, .child_index = 1 },
168 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 21 },
169 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 26 },
170 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 28 },
171 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 30 },
172 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 32 },
173 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 35 },
174 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 36 },
175 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 37 },
176 .{ .char = 'j', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 39 },
177 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 40 },
178 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 41 },
179 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 43 },
180 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 45 },
181 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 49 },
182 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 50 },
183 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 57 },
184 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 61 },
185 .{ .char = 'v', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 64 },
186 .{ .char = 'w', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 66 },
187 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 68 },
188 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 69 },
189 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 70 },
190 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 73 },
191 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 74 },
192 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 75 },
193 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 76 },
194 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 77 },
195 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 82 },
196 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 84 },
197 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 85 },
198 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 86 },
199 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 87 },
200 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 88 },
201 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 89 },
202 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 90 },
203 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 91 },
204 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 92 },
205 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 93 },
206 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 94 },
207 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 95 },
208 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 96 },
209 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 98 },
210 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 99 },
211 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 23, .child_index = 100 },
212 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 108 },
213 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 110 },
214 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 111 },
215 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 112 },
216 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 113 },
217 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 116 },
218 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 117 },
219 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 118 },
220 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 121 },
221 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 122 },
222 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 123 },
223 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 124 },
224 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 125 },
225 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 126 },
226 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 127 },
227 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 128 },
228 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 129 },
229 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 133 },
230 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 134 },
231 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 135 },
232 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 136 },
233 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 137 },
234 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 138 },
235 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 139 },
236 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 140 },
237 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 141 },
238 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 143 },
239 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 144 },
240 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 145 },
241 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 146 },
242 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 147 },
243 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 148 },
244 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 149 },
245 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 150 },
246 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 151 },
247 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 152 },
248 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 153 },
249 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 154 },
250 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 155 },
251 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 157 },
252 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 159 },
253 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 160 },
254 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 161 },
255 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 162 },
256 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 163 },
257 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 164 },
258 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
259 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 165 },
260 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 166 },
261 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 167 },
262 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 168 },
263 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 169 },
264 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 170 },
265 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 172 },
266 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 133 },
267 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 13, .child_index = 173 },
268 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 178 },
269 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 179 },
270 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 181 },
271 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 182 },
272 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 184 },
273 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 185 },
274 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 186 },
275 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 99 },
276 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 187 },
277 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 188 },
278 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 69 },
279 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 172 },
280 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 189 },
281 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 190 },
282 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 191 },
283 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 193 },
284 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 194 },
285 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 195 },
286 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 196 },
287 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 197 },
288 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 150 },
289 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 198 },
290 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 199 },
291 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 200 },
292 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 201 },
293 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 202 },
294 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 203 },
295 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 204 },
296 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 205 },
297 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 206 },
298 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 207 },
299 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 208 },
300 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 150 },
301 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 150 },
302 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 209 },
303 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 210 },
304 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 211 },
305 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 212 },
306 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 213 },
307 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 214 },
308 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 215 },
309 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 216 },
310 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 217 },
311 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 218 },
312 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 219 },
313 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 220 },
314 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 221 },
315 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 222 },
316 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 223 },
317 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
318 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 224 },
319 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 225 },
320 .{ .char = 'y', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
321 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 226 },
322 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 227 },
323 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 228 },
324 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 229 },
325 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 230 },
326 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 231 },
327 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 232 },
328 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 233 },
329 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 234 },
330 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 235 },
331 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 236 },
332 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 237 },
333 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 238 },
334 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 239 },
335 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
336 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 240 },
337 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 241 },
338 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 242 },
339 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
340 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 243 },
341 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 244 },
342 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 246 },
343 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 247 },
344 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 248 },
345 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 251 },
346 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 252 },
347 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 253 },
348 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 254 },
349 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 255 },
350 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 257 },
351 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 258 },
352 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 91 },
353 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 259 },
354 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 260 },
355 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 261 },
356 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 262 },
357 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 263 },
358 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 264 },
359 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 265 },
360 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 266 },
361 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 267 },
362 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 268 },
363 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 269 },
364 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 270 },
365 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 271 },
366 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 272 },
367 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 273 },
368 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 274 },
369 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 275 },
370 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 276 },
371 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 277 },
372 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 278 },
373 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 279 },
374 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 280 },
375 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 133 },
376 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 281 },
377 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 282 },
378 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 283 },
379 .{ .char = 'k', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 285 },
380 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 286 },
381 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 215 },
382 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
383 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 287 },
384 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 288 },
385 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 290 },
386 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
387 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 292 },
388 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 293 },
389 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 294 },
390 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 295 },
391 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 296 },
392 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 297 },
393 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 298 },
394 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 299 },
395 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 300 },
396 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 301 },
397 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 301 },
398 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
399 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 302 },
400 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 303 },
401 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 304 },
402 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 305 },
403 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 306 },
404 .{ .char = 'c', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
405 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 307 },
406 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 308 },
407 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 237 },
408 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 178 },
409 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 309 },
410 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 310 },
411 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 168 },
412 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
413 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 312 },
414 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 313 },
415 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 314 },
416 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 315 },
417 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 316 },
418 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 317 },
419 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 318 },
420 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 151 },
421 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 319 },
422 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 91 },
423 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 320 },
424 .{ .char = 'a', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
425 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 321 },
426 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 322 },
427 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 323 },
428 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 324 },
429 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 325 },
430 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 326 },
431 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 296 },
432 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 327 },
433 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 328 },
434 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 329 },
435 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 224 },
436 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 330 },
437 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 331 },
438 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 112 },
439 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 332 },
440 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 231 },
441 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 333 },
442 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 150 },
443 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 334 },
444 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 335 },
445 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 336 },
446 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 337 },
447 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 338 },
448 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 339 },
449 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 340 },
450 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 341 },
451 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 343 },
452 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 344 },
453 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 345 },
454 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 150 },
455 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 346 },
456 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 348 },
457 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 164 },
458 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 349 },
459 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 350 },
460 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 351 },
461 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 352 },
462 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 353 },
463 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
464 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 300 },
465 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 354 },
466 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 355 },
467 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 356 },
468 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 357 },
469 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 358 },
470 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 359 },
471 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 296 },
472 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 360 },
473 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 361 },
474 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 362 },
475 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 363 },
476 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 364 },
477 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 365 },
478 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 366 },
479 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 367 },
480 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 368 },
481 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 369 },
482 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 370 },
483 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 371 },
484 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 215 },
485 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 172 },
486 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 372 },
487 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 318 },
488 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 373 },
489 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 374 },
490 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 375 },
491 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 376 },
492 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 377 },
493 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 378 },
494 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 379 },
495 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 380 },
496 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 381 },
497 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 382 },
498 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 383 },
499 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 384 },
500 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 385 },
501 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 386 },
502 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 387 },
503 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 388 },
504 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 389 },
505 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 390 },
506 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 391 },
507 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 392 },
508 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 393 },
509 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 394 },
510 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 395 },
511 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 168 },
512 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 396 },
513 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 397 },
514 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 398 },
515 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 399 },
516 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 264 },
517 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 401 },
518 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 402 },
519 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
520 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 395 },
521 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 403 },
522 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 404 },
523 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 405 },
524 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 406 },
525 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 407 },
526 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 408 },
527 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 409 },
528 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 320 },
529 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 410 },
530 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 411 },
531 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 412 },
532 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 413 },
533 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 414 },
534 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 415 },
535 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 416 },
536 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 417 },
537 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 418 },
538 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 419 },
539 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 420 },
540 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 343 },
541 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 296 },
542 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 421 },
543 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 422 },
544 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 423 },
545 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 91 },
546 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 424 },
547 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 425 },
548 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 426 },
549 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 427 },
550 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 428 },
551 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 429 },
552 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 430 },
553 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 383 },
554 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 431 },
555 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 432 },
556 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 433 },
557 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 434 },
558 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 435 },
559 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 436 },
560 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 437 },
561 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 438 },
562 .{ .char = 'g', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
563 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 439 },
564 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 440 },
565 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 441 },
566 .{ .char = 'e', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
567 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 231 },
568 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 442 },
569 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 443 },
570 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 133 },
571 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 444 },
572 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 159 },
573 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 91 },
574 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 445 },
575 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 446 },
576 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 447 },
577 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 448 },
578 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 449 },
579 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 450 },
580 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 451 },
581 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 452 },
582 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 453 },
583 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 273 },
584 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 454 },
585 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 455 },
586 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 456 },
587 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 150 },
588 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
589 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 458 },
590 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 459 },
591 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 460 },
592 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 462 },
593 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 463 },
594 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 153 },
595 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
596 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 464 },
597 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 465 },
598 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 466 },
599 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 467 },
600 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 468 },
601 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 469 },
602 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 398 },
603 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 470 },
604 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 471 },
605 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 472 },
606 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 473 },
607 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 474 },
608 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 172 },
609 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 428 },
610 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 475 },
611 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 476 },
612 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 477 },
613 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 478 },
614 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 395 },
615 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 479 },
616 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 480 },
617 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 208 },
618 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 481 },
619 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 482 },
620 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 483 },
621 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 484 },
622 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 485 },
623 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 486 },
624 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 488 },
625 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 91 },
626 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 467 },
627 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 489 },
628 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 490 },
629 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 491 },
630 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 492 },
631 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 493 },
632 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 494 },
633 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 495 },
634 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
635 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 497 },
636 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 133 },
637 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 153 },
638 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 498 },
639 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 499 },
640 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 500 },
641 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 296 },
642 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 501 },
643 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 502 },
644 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 503 },
645 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 504 },
646 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 505 },
647 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 506 },
648 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 507 },
649 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 508 },
650 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 509 },
651 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 510 },
652 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 511 },
653 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 512 },
654 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 513 },
655 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 514 },
656 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 515 },
657 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 516 },
658 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 215 },
659 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 517 },
660 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 518 },
661 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 519 },
662 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 520 },
663 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 172 },
664 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 521 },
665 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 522 },
666 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 523 },
667 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 524 },
668 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 525 },
669 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 526 },
670 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 527 },
671 .{ .char = 'h', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
672 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 528 },
673 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 237 },
674 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 529 },
675 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 530 },
676 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 531 },
677 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 532 },
678 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 533 },
679 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 534 },
680 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 535 },
681 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 536 },
682 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 537 },
683 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 538 },
684 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 539 },
685 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 378 },
686 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 540 },
687 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 541 },
688 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 133 },
689 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 351 },
690 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 542 },
691 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 543 },
692 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 133 },
693 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 544 },
694 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 545 },
695 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 546 },
696 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 547 },
697 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 548 },
698 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 549 },
699 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 550 },
700 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 554 },
701 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 555 },
702 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 556 },
703 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 557 },
704 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 558 },
705 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 172 },
706 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 559 },
707 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 215 },
708 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 560 },
709 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 561 },
710 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 562 },
711 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 555 },
712 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 563 },
713 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 564 },
714 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 565 },
715 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 566 },
716 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
717 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 567 },
718 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 568 },
719 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 569 },
720 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 570 },
721 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 571 },
722 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 91 },
723 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
724 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 573 },
725 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 574 },
726 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 575 },
727 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 576 },
728 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 577 },
729 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 578 },
730 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 459 },
731 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 579 },
732 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 580 },
733 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 581 },
734 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 582 },
735 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 583 },
736 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 126 },
737 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 584 },
738 .{ .char = 'k', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
739 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 356 },
740 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
741 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 428 },
742 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 586 },
743 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 268 },
744 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 587 },
745 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 588 },
746 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 273 },
747 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 589 },
748 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 590 },
749 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 591 },
750 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 592 },
751 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 593 },
752 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 594 },
753 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 313 },
754 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 595 },
755 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 596 },
756 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 597 },
757 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 598 },
758 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 140 },
759 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 599 },
760 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 600 },
761 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 601 },
762 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 185 },
763 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 602 },
764 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 603 },
765 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 604 },
766 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 605 },
767 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 606 },
768 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 607 },
769 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 608 },
770 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 609 },
771 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 195 },
772 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 610 },
773 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 525 },
774 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 611 },
775 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 215 },
776 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 612 },
777 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 172 },
778 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 613 },
779 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 614 },
780 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 615 },
781 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 616 },
782 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 617 },
783 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 618 },
784 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 619 },
785 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 620 },
786 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 153 },
787 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 621 },
788 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 215 },
789};
790pub const data = blk: {
791 @setEvalBranchQuota(721);
792 break :blk [_]@This(){
793 // access
794 .{ .tag = @enumFromInt(0), .properties = .{ .tag = .access, .gnu = true } },
795 // alias
796 .{ .tag = @enumFromInt(1), .properties = .{ .tag = .alias, .gnu = true } },
797 // align
798 .{ .tag = @enumFromInt(2), .properties = .{ .tag = .aligned, .declspec = true } },
799 // aligned
800 .{ .tag = @enumFromInt(3), .properties = .{ .tag = .aligned, .gnu = true } },
801 // alloc_align
802 .{ .tag = @enumFromInt(4), .properties = .{ .tag = .alloc_align, .gnu = true } },
803 // alloc_size
804 .{ .tag = @enumFromInt(5), .properties = .{ .tag = .alloc_size, .gnu = true } },
805 // allocate
806 .{ .tag = @enumFromInt(6), .properties = .{ .tag = .allocate, .declspec = true } },
807 // allocator
808 .{ .tag = @enumFromInt(7), .properties = .{ .tag = .allocator, .declspec = true } },
809 // always_inline
810 .{ .tag = @enumFromInt(8), .properties = .{ .tag = .always_inline, .gnu = true } },
811 // appdomain
812 .{ .tag = @enumFromInt(9), .properties = .{ .tag = .appdomain, .declspec = true } },
813 // artificial
814 .{ .tag = @enumFromInt(10), .properties = .{ .tag = .artificial, .gnu = true } },
815 // assume_aligned
816 .{ .tag = @enumFromInt(11), .properties = .{ .tag = .assume_aligned, .gnu = true } },
817 // cleanup
818 .{ .tag = @enumFromInt(12), .properties = .{ .tag = .cleanup, .gnu = true } },
819 // code_seg
820 .{ .tag = @enumFromInt(13), .properties = .{ .tag = .code_seg, .declspec = true } },
821 // cold
822 .{ .tag = @enumFromInt(14), .properties = .{ .tag = .cold, .gnu = true } },
823 // common
824 .{ .tag = @enumFromInt(15), .properties = .{ .tag = .common, .gnu = true } },
825 // const
826 .{ .tag = @enumFromInt(16), .properties = .{ .tag = .@"const", .gnu = true } },
827 // constructor
828 .{ .tag = @enumFromInt(17), .properties = .{ .tag = .constructor, .gnu = true } },
829 // copy
830 .{ .tag = @enumFromInt(18), .properties = .{ .tag = .copy, .gnu = true } },
831 // deprecated
832 .{ .tag = @enumFromInt(19), .properties = .{ .tag = .deprecated, .c23 = true, .gnu = true, .declspec = true } },
833 // designated_init
834 .{ .tag = @enumFromInt(20), .properties = .{ .tag = .designated_init, .gnu = true } },
835 // destructor
836 .{ .tag = @enumFromInt(21), .properties = .{ .tag = .destructor, .gnu = true } },
837 // dllexport
838 .{ .tag = @enumFromInt(22), .properties = .{ .tag = .dllexport, .declspec = true } },
839 // dllimport
840 .{ .tag = @enumFromInt(23), .properties = .{ .tag = .dllimport, .declspec = true } },
841 // error
842 .{ .tag = @enumFromInt(24), .properties = .{ .tag = .@"error", .gnu = true } },
843 // externally_visible
844 .{ .tag = @enumFromInt(25), .properties = .{ .tag = .externally_visible, .gnu = true } },
845 // fallthrough
846 .{ .tag = @enumFromInt(26), .properties = .{ .tag = .fallthrough, .c23 = true, .gnu = true } },
847 // flatten
848 .{ .tag = @enumFromInt(27), .properties = .{ .tag = .flatten, .gnu = true } },
849 // format
850 .{ .tag = @enumFromInt(28), .properties = .{ .tag = .format, .gnu = true } },
851 // format_arg
852 .{ .tag = @enumFromInt(29), .properties = .{ .tag = .format_arg, .gnu = true } },
853 // gnu_inline
854 .{ .tag = @enumFromInt(30), .properties = .{ .tag = .gnu_inline, .gnu = true } },
855 // hot
856 .{ .tag = @enumFromInt(31), .properties = .{ .tag = .hot, .gnu = true } },
857 // ifunc
858 .{ .tag = @enumFromInt(32), .properties = .{ .tag = .ifunc, .gnu = true } },
859 // interrupt
860 .{ .tag = @enumFromInt(33), .properties = .{ .tag = .interrupt, .gnu = true } },
861 // interrupt_handler
862 .{ .tag = @enumFromInt(34), .properties = .{ .tag = .interrupt_handler, .gnu = true } },
863 // jitintrinsic
864 .{ .tag = @enumFromInt(35), .properties = .{ .tag = .jitintrinsic, .declspec = true } },
865 // leaf
866 .{ .tag = @enumFromInt(36), .properties = .{ .tag = .leaf, .gnu = true } },
867 // malloc
868 .{ .tag = @enumFromInt(37), .properties = .{ .tag = .malloc, .gnu = true } },
869 // may_alias
870 .{ .tag = @enumFromInt(38), .properties = .{ .tag = .may_alias, .gnu = true } },
871 // maybe_unused
872 .{ .tag = @enumFromInt(39), .properties = .{ .tag = .unused, .c23 = true } },
873 // mode
874 .{ .tag = @enumFromInt(40), .properties = .{ .tag = .mode, .gnu = true } },
875 // naked
876 .{ .tag = @enumFromInt(41), .properties = .{ .tag = .naked, .declspec = true } },
877 // no_address_safety_analysis
878 .{ .tag = @enumFromInt(42), .properties = .{ .tag = .no_address_safety_analysis, .gnu = true } },
879 // no_icf
880 .{ .tag = @enumFromInt(43), .properties = .{ .tag = .no_icf, .gnu = true } },
881 // no_instrument_function
882 .{ .tag = @enumFromInt(44), .properties = .{ .tag = .no_instrument_function, .gnu = true } },
883 // no_profile_instrument_function
884 .{ .tag = @enumFromInt(45), .properties = .{ .tag = .no_profile_instrument_function, .gnu = true } },
885 // no_reorder
886 .{ .tag = @enumFromInt(46), .properties = .{ .tag = .no_reorder, .gnu = true } },
887 // no_sanitize
888 .{ .tag = @enumFromInt(47), .properties = .{ .tag = .no_sanitize, .gnu = true } },
889 // no_sanitize_address
890 .{ .tag = @enumFromInt(48), .properties = .{ .tag = .no_sanitize_address, .gnu = true, .declspec = true } },
891 // no_sanitize_coverage
892 .{ .tag = @enumFromInt(49), .properties = .{ .tag = .no_sanitize_coverage, .gnu = true } },
893 // no_sanitize_thread
894 .{ .tag = @enumFromInt(50), .properties = .{ .tag = .no_sanitize_thread, .gnu = true } },
895 // no_sanitize_undefined
896 .{ .tag = @enumFromInt(51), .properties = .{ .tag = .no_sanitize_undefined, .gnu = true } },
897 // no_split_stack
898 .{ .tag = @enumFromInt(52), .properties = .{ .tag = .no_split_stack, .gnu = true } },
899 // no_stack_limit
900 .{ .tag = @enumFromInt(53), .properties = .{ .tag = .no_stack_limit, .gnu = true } },
901 // no_stack_protector
902 .{ .tag = @enumFromInt(54), .properties = .{ .tag = .no_stack_protector, .gnu = true } },
903 // noalias
904 .{ .tag = @enumFromInt(55), .properties = .{ .tag = .@"noalias", .declspec = true } },
905 // noclone
906 .{ .tag = @enumFromInt(56), .properties = .{ .tag = .noclone, .gnu = true } },
907 // nocommon
908 .{ .tag = @enumFromInt(57), .properties = .{ .tag = .nocommon, .gnu = true } },
909 // nodiscard
910 .{ .tag = @enumFromInt(58), .properties = .{ .tag = .nodiscard, .c23 = true } },
911 // noinit
912 .{ .tag = @enumFromInt(59), .properties = .{ .tag = .noinit, .gnu = true } },
913 // noinline
914 .{ .tag = @enumFromInt(60), .properties = .{ .tag = .@"noinline", .gnu = true, .declspec = true } },
915 // noipa
916 .{ .tag = @enumFromInt(61), .properties = .{ .tag = .noipa, .gnu = true } },
917 // nonstring
918 .{ .tag = @enumFromInt(62), .properties = .{ .tag = .nonstring, .gnu = true } },
919 // noplt
920 .{ .tag = @enumFromInt(63), .properties = .{ .tag = .noplt, .gnu = true } },
921 // noreturn
922 .{ .tag = @enumFromInt(64), .properties = .{ .tag = .@"noreturn", .c23 = true, .gnu = true, .declspec = true } },
923 // packed
924 .{ .tag = @enumFromInt(65), .properties = .{ .tag = .@"packed", .gnu = true } },
925 // patchable_function_entry
926 .{ .tag = @enumFromInt(66), .properties = .{ .tag = .patchable_function_entry, .gnu = true } },
927 // persistent
928 .{ .tag = @enumFromInt(67), .properties = .{ .tag = .persistent, .gnu = true } },
929 // process
930 .{ .tag = @enumFromInt(68), .properties = .{ .tag = .process, .declspec = true } },
931 // pure
932 .{ .tag = @enumFromInt(69), .properties = .{ .tag = .pure, .gnu = true } },
933 // reproducible
934 .{ .tag = @enumFromInt(70), .properties = .{ .tag = .reproducible, .c23 = true } },
935 // restrict
936 .{ .tag = @enumFromInt(71), .properties = .{ .tag = .restrict, .declspec = true } },
937 // retain
938 .{ .tag = @enumFromInt(72), .properties = .{ .tag = .retain, .gnu = true } },
939 // returns_nonnull
940 .{ .tag = @enumFromInt(73), .properties = .{ .tag = .returns_nonnull, .gnu = true } },
941 // returns_twice
942 .{ .tag = @enumFromInt(74), .properties = .{ .tag = .returns_twice, .gnu = true } },
943 // safebuffers
944 .{ .tag = @enumFromInt(75), .properties = .{ .tag = .safebuffers, .declspec = true } },
945 // scalar_storage_order
946 .{ .tag = @enumFromInt(76), .properties = .{ .tag = .scalar_storage_order, .gnu = true } },
947 // section
948 .{ .tag = @enumFromInt(77), .properties = .{ .tag = .section, .gnu = true } },
949 // selectany
950 .{ .tag = @enumFromInt(78), .properties = .{ .tag = .selectany, .declspec = true } },
951 // sentinel
952 .{ .tag = @enumFromInt(79), .properties = .{ .tag = .sentinel, .gnu = true } },
953 // simd
954 .{ .tag = @enumFromInt(80), .properties = .{ .tag = .simd, .gnu = true } },
955 // spectre
956 .{ .tag = @enumFromInt(81), .properties = .{ .tag = .spectre, .declspec = true } },
957 // stack_protect
958 .{ .tag = @enumFromInt(82), .properties = .{ .tag = .stack_protect, .gnu = true } },
959 // symver
960 .{ .tag = @enumFromInt(83), .properties = .{ .tag = .symver, .gnu = true } },
961 // target
962 .{ .tag = @enumFromInt(84), .properties = .{ .tag = .target, .gnu = true } },
963 // target_clones
964 .{ .tag = @enumFromInt(85), .properties = .{ .tag = .target_clones, .gnu = true } },
965 // thread
966 .{ .tag = @enumFromInt(86), .properties = .{ .tag = .thread, .declspec = true } },
967 // tls_model
968 .{ .tag = @enumFromInt(87), .properties = .{ .tag = .tls_model, .gnu = true } },
969 // transparent_union
970 .{ .tag = @enumFromInt(88), .properties = .{ .tag = .transparent_union, .gnu = true } },
971 // unavailable
972 .{ .tag = @enumFromInt(89), .properties = .{ .tag = .unavailable, .gnu = true } },
973 // uninitialized
974 .{ .tag = @enumFromInt(90), .properties = .{ .tag = .uninitialized, .gnu = true } },
975 // unsequenced
976 .{ .tag = @enumFromInt(91), .properties = .{ .tag = .unsequenced, .c23 = true } },
977 // unused
978 .{ .tag = @enumFromInt(92), .properties = .{ .tag = .unused, .gnu = true } },
979 // used
980 .{ .tag = @enumFromInt(93), .properties = .{ .tag = .used, .gnu = true } },
981 // uuid
982 .{ .tag = @enumFromInt(94), .properties = .{ .tag = .uuid, .declspec = true } },
983 // vector_size
984 .{ .tag = @enumFromInt(95), .properties = .{ .tag = .vector_size, .gnu = true } },
985 // visibility
986 .{ .tag = @enumFromInt(96), .properties = .{ .tag = .visibility, .gnu = true } },
987 // warn_if_not_aligned
988 .{ .tag = @enumFromInt(97), .properties = .{ .tag = .warn_if_not_aligned, .gnu = true } },
989 // warn_unused_result
990 .{ .tag = @enumFromInt(98), .properties = .{ .tag = .warn_unused_result, .gnu = true } },
991 // warning
992 .{ .tag = @enumFromInt(99), .properties = .{ .tag = .warning, .gnu = true } },
993 // weak
994 .{ .tag = @enumFromInt(100), .properties = .{ .tag = .weak, .gnu = true } },
995 // weakref
996 .{ .tag = @enumFromInt(101), .properties = .{ .tag = .weakref, .gnu = true } },
997 // zero_call_used_regs
998 .{ .tag = @enumFromInt(102), .properties = .{ .tag = .zero_call_used_regs, .gnu = true } },
999 };
1000};
1001};
1002}
lib/compiler/aro/aro/Builtins.zig deleted-394
...@@ -1,394 +0,0 @@
1const std = @import("std");
2const Compilation = @import("Compilation.zig");
3const Type = @import("Type.zig");
4const TypeDescription = @import("Builtins/TypeDescription.zig");
5const target_util = @import("target.zig");
6const StringId = @import("StringInterner.zig").StringId;
7const LangOpts = @import("LangOpts.zig");
8const Parser = @import("Parser.zig");
9
10const Properties = @import("Builtins/Properties.zig");
11pub const Builtin = @import("Builtins/Builtin.zig").with(Properties);
12
13const Expanded = struct {
14 ty: Type,
15 builtin: Builtin,
16};
17
18const NameToTypeMap = std.StringHashMapUnmanaged(Type);
19
20const Builtins = @This();
21
22_name_to_type_map: NameToTypeMap = .{},
23
24pub fn deinit(b: *Builtins, gpa: std.mem.Allocator) void {
25 b._name_to_type_map.deinit(gpa);
26}
27
28fn specForSize(comp: *const Compilation, size_bits: u32) Type.Builder.Specifier {
29 var ty = Type{ .specifier = .short };
30 if (ty.sizeof(comp).? * 8 == size_bits) return .short;
31
32 ty.specifier = .int;
33 if (ty.sizeof(comp).? * 8 == size_bits) return .int;
34
35 ty.specifier = .long;
36 if (ty.sizeof(comp).? * 8 == size_bits) return .long;
37
38 ty.specifier = .long_long;
39 if (ty.sizeof(comp).? * 8 == size_bits) return .long_long;
40
41 unreachable;
42}
43
44fn createType(desc: TypeDescription, it: *TypeDescription.TypeIterator, comp: *const Compilation, allocator: std.mem.Allocator) !Type {
45 var builder: Type.Builder = .{ .error_on_invalid = true };
46 var require_native_int32 = false;
47 var require_native_int64 = false;
48 for (desc.prefix) |prefix| {
49 switch (prefix) {
50 .L => builder.combine(undefined, .long, 0) catch unreachable,
51 .LL => {
52 builder.combine(undefined, .long, 0) catch unreachable;
53 builder.combine(undefined, .long, 0) catch unreachable;
54 },
55 .LLL => {
56 switch (builder.specifier) {
57 .none => builder.specifier = .int128,
58 .signed => builder.specifier = .sint128,
59 .unsigned => builder.specifier = .uint128,
60 else => unreachable,
61 }
62 },
63 .Z => require_native_int32 = true,
64 .W => require_native_int64 = true,
65 .N => {
66 std.debug.assert(desc.spec == .i);
67 if (!target_util.isLP64(comp.target)) {
68 builder.combine(undefined, .long, 0) catch unreachable;
69 }
70 },
71 .O => {
72 builder.combine(undefined, .long, 0) catch unreachable;
73 if (comp.target.os.tag != .opencl) {
74 builder.combine(undefined, .long, 0) catch unreachable;
75 }
76 },
77 .S => builder.combine(undefined, .signed, 0) catch unreachable,
78 .U => builder.combine(undefined, .unsigned, 0) catch unreachable,
79 .I => {
80 // Todo: compile-time constant integer
81 },
82 }
83 }
84 switch (desc.spec) {
85 .v => builder.combine(undefined, .void, 0) catch unreachable,
86 .b => builder.combine(undefined, .bool, 0) catch unreachable,
87 .c => builder.combine(undefined, .char, 0) catch unreachable,
88 .s => builder.combine(undefined, .short, 0) catch unreachable,
89 .i => {
90 if (require_native_int32) {
91 builder.specifier = specForSize(comp, 32);
92 } else if (require_native_int64) {
93 builder.specifier = specForSize(comp, 64);
94 } else {
95 switch (builder.specifier) {
96 .int128, .sint128, .uint128 => {},
97 else => builder.combine(undefined, .int, 0) catch unreachable,
98 }
99 }
100 },
101 .h => builder.combine(undefined, .fp16, 0) catch unreachable,
102 .x => builder.combine(undefined, .float16, 0) catch unreachable,
103 .y => {
104 // Todo: __bf16
105 return .{ .specifier = .invalid };
106 },
107 .f => builder.combine(undefined, .float, 0) catch unreachable,
108 .d => {
109 if (builder.specifier == .long_long) {
110 builder.specifier = .float128;
111 } else {
112 builder.combine(undefined, .double, 0) catch unreachable;
113 }
114 },
115 .z => {
116 std.debug.assert(builder.specifier == .none);
117 builder.specifier = Type.Builder.fromType(comp.types.size);
118 },
119 .w => {
120 std.debug.assert(builder.specifier == .none);
121 builder.specifier = Type.Builder.fromType(comp.types.wchar);
122 },
123 .F => {
124 std.debug.assert(builder.specifier == .none);
125 builder.specifier = Type.Builder.fromType(comp.types.ns_constant_string.ty);
126 },
127 .G => {
128 // Todo: id
129 return .{ .specifier = .invalid };
130 },
131 .H => {
132 // Todo: SEL
133 return .{ .specifier = .invalid };
134 },
135 .M => {
136 // Todo: struct objc_super
137 return .{ .specifier = .invalid };
138 },
139 .a => {
140 std.debug.assert(builder.specifier == .none);
141 std.debug.assert(desc.suffix.len == 0);
142 builder.specifier = Type.Builder.fromType(comp.types.va_list);
143 },
144 .A => {
145 std.debug.assert(builder.specifier == .none);
146 std.debug.assert(desc.suffix.len == 0);
147 var va_list = comp.types.va_list;
148 if (va_list.isArray()) va_list.decayArray();
149 builder.specifier = Type.Builder.fromType(va_list);
150 },
151 .V => |element_count| {
152 std.debug.assert(desc.suffix.len == 0);
153 const child_desc = it.next().?;
154 const child_ty = try createType(child_desc, undefined, comp, allocator);
155 const arr_ty = try allocator.create(Type.Array);
156 arr_ty.* = .{
157 .len = element_count,
158 .elem = child_ty,
159 };
160 const vector_ty: Type = .{ .specifier = .vector, .data = .{ .array = arr_ty } };
161 builder.specifier = Type.Builder.fromType(vector_ty);
162 },
163 .q => {
164 // Todo: scalable vector
165 return .{ .specifier = .invalid };
166 },
167 .E => {
168 // Todo: ext_vector (OpenCL vector)
169 return .{ .specifier = .invalid };
170 },
171 .X => |child| {
172 builder.combine(undefined, .complex, 0) catch unreachable;
173 switch (child) {
174 .float => builder.combine(undefined, .float, 0) catch unreachable,
175 .double => builder.combine(undefined, .double, 0) catch unreachable,
176 .longdouble => {
177 builder.combine(undefined, .long, 0) catch unreachable;
178 builder.combine(undefined, .double, 0) catch unreachable;
179 },
180 }
181 },
182 .Y => {
183 std.debug.assert(builder.specifier == .none);
184 std.debug.assert(desc.suffix.len == 0);
185 builder.specifier = Type.Builder.fromType(comp.types.ptrdiff);
186 },
187 .P => {
188 std.debug.assert(builder.specifier == .none);
189 if (comp.types.file.specifier == .invalid) {
190 return comp.types.file;
191 }
192 builder.specifier = Type.Builder.fromType(comp.types.file);
193 },
194 .J => {
195 std.debug.assert(builder.specifier == .none);
196 std.debug.assert(desc.suffix.len == 0);
197 if (comp.types.jmp_buf.specifier == .invalid) {
198 return comp.types.jmp_buf;
199 }
200 builder.specifier = Type.Builder.fromType(comp.types.jmp_buf);
201 },
202 .SJ => {
203 std.debug.assert(builder.specifier == .none);
204 std.debug.assert(desc.suffix.len == 0);
205 if (comp.types.sigjmp_buf.specifier == .invalid) {
206 return comp.types.sigjmp_buf;
207 }
208 builder.specifier = Type.Builder.fromType(comp.types.sigjmp_buf);
209 },
210 .K => {
211 std.debug.assert(builder.specifier == .none);
212 if (comp.types.ucontext_t.specifier == .invalid) {
213 return comp.types.ucontext_t;
214 }
215 builder.specifier = Type.Builder.fromType(comp.types.ucontext_t);
216 },
217 .p => {
218 std.debug.assert(builder.specifier == .none);
219 std.debug.assert(desc.suffix.len == 0);
220 builder.specifier = Type.Builder.fromType(comp.types.pid_t);
221 },
222 .@"!" => return .{ .specifier = .invalid },
223 }
224 for (desc.suffix) |suffix| {
225 switch (suffix) {
226 .@"*" => |address_space| {
227 _ = address_space; // TODO: handle address space
228 const elem_ty = try allocator.create(Type);
229 elem_ty.* = builder.finish(undefined) catch unreachable;
230 const ty = Type{
231 .specifier = .pointer,
232 .data = .{ .sub_type = elem_ty },
233 };
234 builder.qual = .{};
235 builder.specifier = Type.Builder.fromType(ty);
236 },
237 .C => builder.qual.@"const" = 0,
238 .D => builder.qual.@"volatile" = 0,
239 .R => builder.qual.restrict = 0,
240 }
241 }
242 return builder.finish(undefined) catch unreachable;
243}
244
245fn createBuiltin(comp: *const Compilation, builtin: Builtin, type_arena: std.mem.Allocator) !Type {
246 var it = TypeDescription.TypeIterator.init(builtin.properties.param_str);
247
248 const ret_ty_desc = it.next().?;
249 if (ret_ty_desc.spec == .@"!") {
250 // Todo: handle target-dependent definition
251 }
252 const ret_ty = try createType(ret_ty_desc, &it, comp, type_arena);
253 var param_count: usize = 0;
254 var params: [Builtin.max_param_count]Type.Func.Param = undefined;
255 while (it.next()) |desc| : (param_count += 1) {
256 params[param_count] = .{ .name_tok = 0, .ty = try createType(desc, &it, comp, type_arena), .name = .empty };
257 }
258
259 const duped_params = try type_arena.dupe(Type.Func.Param, params[0..param_count]);
260 const func = try type_arena.create(Type.Func);
261
262 func.* = .{
263 .return_type = ret_ty,
264 .params = duped_params,
265 };
266 return .{
267 .specifier = if (builtin.properties.isVarArgs()) .var_args_func else .func,
268 .data = .{ .func = func },
269 };
270}
271
272/// Asserts that the builtin has already been created
273pub fn lookup(b: *const Builtins, name: []const u8) Expanded {
274 const builtin = Builtin.fromName(name).?;
275 const ty = b._name_to_type_map.get(name).?;
276 return .{
277 .builtin = builtin,
278 .ty = ty,
279 };
280}
281
282pub fn getOrCreate(b: *Builtins, comp: *Compilation, name: []const u8, type_arena: std.mem.Allocator) !?Expanded {
283 const ty = b._name_to_type_map.get(name) orelse {
284 const builtin = Builtin.fromName(name) orelse return null;
285 if (!comp.hasBuiltinFunction(builtin)) return null;
286
287 try b._name_to_type_map.ensureUnusedCapacity(comp.gpa, 1);
288 const ty = try createBuiltin(comp, builtin, type_arena);
289 b._name_to_type_map.putAssumeCapacity(name, ty);
290
291 return .{
292 .builtin = builtin,
293 .ty = ty,
294 };
295 };
296 const builtin = Builtin.fromName(name).?;
297 return .{
298 .builtin = builtin,
299 .ty = ty,
300 };
301}
302
303pub const Iterator = struct {
304 index: u16 = 1,
305 name_buf: [Builtin.longest_name]u8 = undefined,
306
307 pub const Entry = struct {
308 /// Memory of this slice is overwritten on every call to `next`
309 name: []const u8,
310 builtin: Builtin,
311 };
312
313 pub fn next(self: *Iterator) ?Entry {
314 if (self.index > Builtin.data.len) return null;
315 const index = self.index;
316 const data_index = index - 1;
317 self.index += 1;
318 return .{
319 .name = Builtin.nameFromUniqueIndex(index, &self.name_buf),
320 .builtin = Builtin.data[data_index],
321 };
322 }
323};
324
325test Iterator {
326 var it = Iterator{};
327
328 var seen = std.StringHashMap(Builtin).init(std.testing.allocator);
329 defer seen.deinit();
330
331 var arena_state = std.heap.ArenaAllocator.init(std.testing.allocator);
332 defer arena_state.deinit();
333 const arena = arena_state.allocator();
334
335 while (it.next()) |entry| {
336 const index = Builtin.uniqueIndex(entry.name).?;
337 var buf: [Builtin.longest_name]u8 = undefined;
338 const name_from_index = Builtin.nameFromUniqueIndex(index, &buf);
339 try std.testing.expectEqualStrings(entry.name, name_from_index);
340
341 if (seen.contains(entry.name)) {
342 std.debug.print("iterated over {s} twice\n", .{entry.name});
343 std.debug.print("current data: {}\n", .{entry.builtin});
344 std.debug.print("previous data: {}\n", .{seen.get(entry.name).?});
345 return error.TestExpectedUniqueEntries;
346 }
347 try seen.put(try arena.dupe(u8, entry.name), entry.builtin);
348 }
349 try std.testing.expectEqual(@as(usize, Builtin.data.len), seen.count());
350}
351
352test "All builtins" {
353 var comp = Compilation.init(std.testing.allocator, std.fs.cwd());
354 defer comp.deinit();
355 _ = try comp.generateBuiltinMacros(.include_system_defines);
356 var arena = std.heap.ArenaAllocator.init(std.testing.allocator);
357 defer arena.deinit();
358
359 const type_arena = arena.allocator();
360
361 var builtin_it = Iterator{};
362 while (builtin_it.next()) |entry| {
363 const name = try type_arena.dupe(u8, entry.name);
364 if (try comp.builtins.getOrCreate(&comp, name, type_arena)) |func_ty| {
365 const get_again = (try comp.builtins.getOrCreate(&comp, name, std.testing.failing_allocator)).?;
366 const found_by_lookup = comp.builtins.lookup(name);
367 try std.testing.expectEqual(func_ty.builtin.tag, get_again.builtin.tag);
368 try std.testing.expectEqual(func_ty.builtin.tag, found_by_lookup.builtin.tag);
369 }
370 }
371}
372
373test "Allocation failures" {
374 const Test = struct {
375 fn testOne(allocator: std.mem.Allocator) !void {
376 var comp = Compilation.init(allocator, std.fs.cwd());
377 defer comp.deinit();
378 _ = try comp.generateBuiltinMacros(.include_system_defines);
379 var arena = std.heap.ArenaAllocator.init(comp.gpa);
380 defer arena.deinit();
381
382 const type_arena = arena.allocator();
383
384 const num_builtins = 40;
385 var builtin_it = Iterator{};
386 for (0..num_builtins) |_| {
387 const entry = builtin_it.next().?;
388 _ = try comp.builtins.getOrCreate(&comp, entry.name, type_arena);
389 }
390 }
391 };
392
393 try std.testing.checkAllAllocationFailures(std.testing.allocator, Test.testOne, .{});
394}
lib/compiler/aro/aro/Builtins/Builtin.zig deleted-13146
...@@ -1,13146 +0,0 @@
1//! Autogenerated by GenerateDef from src/aro/Builtins/Builtin.def, do not edit
2// zig fmt: off
3
4const std = @import("std");
5
6pub fn with(comptime Properties: type) type {
7return struct {
8const TargetSet = Properties.TargetSet;
9pub const max_param_count = 12;
10
11tag: Tag,
12properties: Properties,
13
14/// Integer starting at 0 derived from the unique index,
15/// corresponds with the data array index.
16pub const Tag = enum(u16) { _ };
17
18const Self = @This();
19
20pub fn fromName(name: []const u8) ?@This() {
21 const data_index = tagFromName(name) orelse return null;
22 return data[@intFromEnum(data_index)];
23}
24
25pub fn tagFromName(name: []const u8) ?Tag {
26 const unique_index = uniqueIndex(name) orelse return null;
27 return @enumFromInt(unique_index - 1);
28}
29
30pub fn fromTag(tag: Tag) @This() {
31 return data[@intFromEnum(tag)];
32}
33
34pub fn nameFromTagIntoBuf(tag: Tag, name_buf: []u8) []u8 {
35 std.debug.assert(name_buf.len >= longest_name);
36 const unique_index = @intFromEnum(tag) + 1;
37 return nameFromUniqueIndex(unique_index, name_buf);
38}
39
40pub fn nameFromTag(tag: Tag) NameBuf {
41 var name_buf: NameBuf = undefined;
42 const unique_index = @intFromEnum(tag) + 1;
43 const name = nameFromUniqueIndex(unique_index, &name_buf.buf);
44 name_buf.len = @intCast(name.len);
45 return name_buf;
46}
47
48pub const NameBuf = struct {
49 buf: [longest_name]u8 = undefined,
50 len: std.math.IntFittingRange(0, longest_name),
51
52 pub fn span(self: *const NameBuf) []const u8 {
53 return self.buf[0..self.len];
54 }
55};
56
57pub fn exists(name: []const u8) bool {
58 if (name.len < shortest_name or name.len > longest_name) return false;
59
60 var index: u16 = 0;
61 for (name) |c| {
62 index = findInList(dafsa[index].child_index, c) orelse return false;
63 }
64 return dafsa[index].end_of_word;
65}
66
67pub const shortest_name = 3;
68pub const longest_name = 43;
69
70/// Search siblings of `first_child_index` for the `char`
71/// If found, returns the index of the node within the `dafsa` array.
72/// Otherwise, returns `null`.
73pub fn findInList(first_child_index: u16, char: u8) ?u16 {
74 @setEvalBranchQuota(7972);
75 var index = first_child_index;
76 while (true) {
77 if (dafsa[index].char == char) return index;
78 if (dafsa[index].end_of_list) return null;
79 index += 1;
80 }
81 unreachable;
82}
83
84/// Returns a unique (minimal perfect hash) index (starting at 1) for the `name`,
85/// or null if the name was not found.
86pub fn uniqueIndex(name: []const u8) ?u16 {
87 if (name.len < shortest_name or name.len > longest_name) return null;
88
89 var index: u16 = 0;
90 var node_index: u16 = 0;
91
92 for (name) |c| {
93 const child_index = findInList(dafsa[node_index].child_index, c) orelse return null;
94 var sibling_index = dafsa[node_index].child_index;
95 while (true) {
96 const sibling_c = dafsa[sibling_index].char;
97 std.debug.assert(sibling_c != 0);
98 if (sibling_c < c) {
99 index += dafsa[sibling_index].number;
100 }
101 if (dafsa[sibling_index].end_of_list) break;
102 sibling_index += 1;
103 }
104 node_index = child_index;
105 if (dafsa[node_index].end_of_word) index += 1;
106 }
107
108 if (!dafsa[node_index].end_of_word) return null;
109
110 return index;
111}
112
113/// Returns a slice of `buf` with the name associated with the given `index`.
114/// This function should only be called with an `index` that
115/// is already known to exist within the `dafsa`, e.g. an index
116/// returned from `uniqueIndex`.
117pub fn nameFromUniqueIndex(index: u16, buf: []u8) []u8 {
118 std.debug.assert(index >= 1 and index <= data.len);
119
120 var node_index: u16 = 0;
121 var count: u16 = index;
122 var fbs = std.io.fixedBufferStream(buf);
123 const w = fbs.writer();
124
125 while (true) {
126 var sibling_index = dafsa[node_index].child_index;
127 while (true) {
128 if (dafsa[sibling_index].number > 0 and dafsa[sibling_index].number < count) {
129 count -= dafsa[sibling_index].number;
130 } else {
131 w.writeByte(dafsa[sibling_index].char) catch unreachable;
132 node_index = sibling_index;
133 if (dafsa[node_index].end_of_word) {
134 count -= 1;
135 }
136 break;
137 }
138
139 if (dafsa[sibling_index].end_of_list) break;
140 sibling_index += 1;
141 }
142 if (count == 0) break;
143 }
144
145 return fbs.getWritten();
146}
147
148/// We're 1 bit shy of being able to fit this in a u32:
149/// - char only contains 0-9, a-z, A-Z, and _, so it could use a enum(u6) with a way to convert <-> u8
150/// (note: this would have a performance cost that may make the u32 not worth it)
151/// - number has a max value of > 2047 and < 4095 (the first _ node has the largest number),
152/// so it could fit into a u12
153/// - child_index currently has a max of > 4095 and < 8191, so it could fit into a u13
154///
155/// with the end_of_word/end_of_list 2 bools, that makes 33 bits total
156const Node = packed struct(u64) {
157 char: u8,
158 /// Nodes are numbered with "an integer which gives the number of words that
159 /// would be accepted by the automaton starting from that state." This numbering
160 /// allows calculating "a one-to-one correspondence between the integers 1 to L
161 /// (L is the number of words accepted by the automaton) and the words themselves."
162 ///
163 /// Essentially, this allows us to have a minimal perfect hashing scheme such that
164 /// it's possible to store & lookup the properties of each builtin using a separate array.
165 number: u16,
166 /// If true, this node is the end of a valid builtin.
167 /// Note: This does not necessarily mean that this node does not have child nodes.
168 end_of_word: bool,
169 /// If true, this node is the end of a sibling list.
170 /// If false, then (index + 1) will contain the next sibling.
171 end_of_list: bool,
172 /// Padding bits to get to u64, unsure if there's some way to use these to improve something.
173 _extra: u22 = 0,
174 /// Index of the first child of this node.
175 child_index: u16,
176};
177
178const dafsa = [_]Node{
179 .{ .char = 0, .end_of_word = false, .end_of_list = true, .number = 0, .child_index = 1 },
180 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 3639, .child_index = 19 },
181 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 25, .child_index = 32 },
182 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 37 },
183 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 82, .child_index = 39 },
184 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 50 },
185 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 33, .child_index = 52 },
186 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 62 },
187 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 63 },
188 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 64 },
189 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 36, .child_index = 67 },
190 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 73 },
191 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 76 },
192 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 78 },
193 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 17, .child_index = 80 },
194 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 54, .child_index = 83 },
195 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 14, .child_index = 92 },
196 .{ .char = 'v', .end_of_word = false, .end_of_list = false, .number = 11, .child_index = 96 },
197 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 100 },
198 .{ .char = 'B', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 102 },
199 .{ .char = 'E', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 103 },
200 .{ .char = 'I', .end_of_word = false, .end_of_list = false, .number = 29, .child_index = 104 },
201 .{ .char = 'M', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 105 },
202 .{ .char = 'R', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 106 },
203 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 3563, .child_index = 107 },
204 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 125 },
205 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 11, .child_index = 127 },
206 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 129 },
207 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 130 },
208 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 131 },
209 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 133 },
210 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 134 },
211 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 135 },
212 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 137 },
213 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 138 },
214 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 140 },
215 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 141 },
216 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 142 },
217 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 144 },
218 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 25, .child_index = 145 },
219 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 151 },
220 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 137 },
221 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 152 },
222 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 154 },
223 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 155 },
224 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 156 },
225 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 159 },
226 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 161 },
227 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 162 },
228 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 164 },
229 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 165 },
230 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 166 },
231 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 168 },
232 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 169 },
233 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 170 },
234 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 171 },
235 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 172 },
236 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 175 },
237 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 176 },
238 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 177 },
239 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 178 },
240 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 179 },
241 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 180 },
242 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 181 },
243 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 182 },
244 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 183 },
245 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 184 },
246 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 194 },
247 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 195 },
248 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 196 },
249 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 197 },
250 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 199 },
251 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 201 },
252 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 203 },
253 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 204 },
254 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 205 },
255 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 206 },
256 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 207 },
257 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 209 },
258 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 210 },
259 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 211 },
260 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 213 },
261 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 214 },
262 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 215 },
263 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 216 },
264 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 217 },
265 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 218 },
266 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 220 },
267 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 176 },
268 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 151 },
269 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 178 },
270 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 31, .child_index = 221 },
271 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 223 },
272 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 196 },
273 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 224 },
274 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 226 },
275 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 227 },
276 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 228 },
277 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 176 },
278 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 231 },
279 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 235 },
280 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 236 },
281 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 237 },
282 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 238 },
283 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 29, .child_index = 239 },
284 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 240 },
285 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 241 },
286 .{ .char = 'G', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 242 },
287 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 34, .child_index = 243 },
288 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 2967, .child_index = 248 },
289 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 20, .child_index = 249 },
290 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 252 },
291 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 255 },
292 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 257 },
293 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 259 },
294 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 260 },
295 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 390, .child_index = 262 },
296 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 264 },
297 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 265 },
298 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 113, .child_index = 266 },
299 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 269 },
300 .{ .char = 'v', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 270 },
301 .{ .char = 'w', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 271 },
302 .{ .char = 'x', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 273 },
303 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 274 },
304 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 275 },
305 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 276 },
306 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 277 },
307 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 278 },
308 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 279 },
309 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 281 },
310 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 282 },
311 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 283 },
312 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 284 },
313 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 285 },
314 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 286 },
315 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
316 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 287 },
317 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 288 },
318 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 289 },
319 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 223 },
320 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 290 },
321 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 291 },
322 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 292 },
323 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 293 },
324 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 294 },
325 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 137 },
326 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 295 },
327 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 296 },
328 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 140 },
329 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 164 },
330 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 297 },
331 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 298 },
332 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 299 },
333 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 300 },
334 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 296 },
335 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 301 },
336 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 302 },
337 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 303 },
338 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 209 },
339 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 306 },
340 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 307 },
341 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 223 },
342 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 151 },
343 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 223 },
344 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 308 },
345 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 311 },
346 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 9, .child_index = 312 },
347 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 294 },
348 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 316 },
349 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 317 },
350 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 318 },
351 .{ .char = 'a', .end_of_word = true, .end_of_list = false, .number = 6, .child_index = 319 },
352 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 206 },
353 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 322 },
354 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 323 },
355 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 210 },
356 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 324 },
357 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 327 },
358 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 328 },
359 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 329 },
360 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 330 },
361 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 331 },
362 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 332 },
363 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 333 },
364 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 334 },
365 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 335 },
366 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 336 },
367 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 337 },
368 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 338 },
369 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 339 },
370 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 341 },
371 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 342 },
372 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 343 },
373 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 344 },
374 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 345 },
375 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 346 },
376 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 194 },
377 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 201 },
378 .{ .char = 'g', .end_of_word = true, .end_of_list = false, .number = 15, .child_index = 347 },
379 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 352 },
380 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 353 },
381 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 354 },
382 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 295 },
383 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 355 },
384 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 360 },
385 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
386 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 363 },
387 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 364 },
388 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
389 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 365 },
390 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 203 },
391 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 366 },
392 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 368 },
393 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 370 },
394 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 371 },
395 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 7, .child_index = 372 },
396 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 374 },
397 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 375 },
398 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 303 },
399 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 176 },
400 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 377 },
401 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 29, .child_index = 379 },
402 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 303 },
403 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 338 },
404 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 342 },
405 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 389 },
406 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 390 },
407 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 393 },
408 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 176 },
409 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 178 },
410 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 327 },
411 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 220 },
412 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 176 },
413 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 178 },
414 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 394 },
415 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 397 },
416 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 398 },
417 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
418 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 29, .child_index = 399 },
419 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 400 },
420 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 401 },
421 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 402 },
422 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 275 },
423 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 403 },
424 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 404 },
425 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 405 },
426 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 30, .child_index = 406 },
427 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2967, .child_index = 407 },
428 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 17, .child_index = 408 },
429 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 409 },
430 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 410 },
431 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 411 },
432 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 412 },
433 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 412 },
434 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 238 },
435 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 413 },
436 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 415 },
437 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 170 },
438 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 416 },
439 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 418 },
440 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 419 },
441 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 420 },
442 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 389, .child_index = 421 },
443 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 422 },
444 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 423 },
445 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 424 },
446 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 425 },
447 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 108, .child_index = 427 },
448 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 428 },
449 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 429 },
450 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 430 },
451 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 431 },
452 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 433 },
453 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 434 },
454 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 435 },
455 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 289 },
456 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 436 },
457 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 437 },
458 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 438 },
459 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
460 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 439 },
461 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 352 },
462 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 440 },
463 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 441 },
464 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 443 },
465 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
466 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 303 },
467 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 444 },
468 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 445 },
469 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 9, .child_index = 446 },
470 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
471 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 450 },
472 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 451 },
473 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
474 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 452 },
475 .{ .char = 'g', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
476 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
477 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
478 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
479 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 296 },
480 .{ .char = 'j', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
481 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 453 },
482 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
483 .{ .char = 'h', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 361 },
484 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
485 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 301 },
486 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 298 },
487 .{ .char = 'c', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 361 },
488 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
489 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
490 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
491 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 361 },
492 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
493 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
494 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 454 },
495 .{ .char = 'm', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
496 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 455 },
497 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 456 },
498 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
499 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
500 .{ .char = 'x', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
501 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
502 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
503 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 458 },
504 .{ .char = 'e', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
505 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 299 },
506 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 459 },
507 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 460 },
508 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 461 },
509 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 297 },
510 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 462 },
511 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 463 },
512 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 464 },
513 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 466 },
514 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 467 },
515 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 468 },
516 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 469 },
517 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 470 },
518 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 471 },
519 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 472 },
520 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 473 },
521 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 474 },
522 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 336 },
523 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
524 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 299 },
525 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 475 },
526 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 476 },
527 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 361 },
528 .{ .char = 'b', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 361 },
529 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
530 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
531 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 374 },
532 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 297 },
533 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 478 },
534 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 479 },
535 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 480 },
536 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 484 },
537 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 485 },
538 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 486 },
539 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
540 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
541 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
542 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 487 },
543 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 488 },
544 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 490 },
545 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 491 },
546 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 492 },
547 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 332 },
548 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
549 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 493 },
550 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 494 },
551 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 495 },
552 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
553 .{ .char = 'j', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 497 },
554 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 498 },
555 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 499 },
556 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 292 },
557 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 485 },
558 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 500 },
559 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 505 },
560 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 506 },
561 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 507 },
562 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 509 },
563 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 511 },
564 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 512 },
565 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 513 },
566 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 515 },
567 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 516 },
568 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 517 },
569 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 518 },
570 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 519 },
571 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 520 },
572 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 521 },
573 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 522 },
574 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 323 },
575 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 524 },
576 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 525 },
577 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 527 },
578 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 29, .child_index = 528 },
579 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 529 },
580 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 531 },
581 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 532 },
582 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 533 },
583 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 534 },
584 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 535 },
585 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 30, .child_index = 536 },
586 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2967, .child_index = 537 },
587 .{ .char = '1', .end_of_word = false, .end_of_list = true, .number = 17, .child_index = 538 },
588 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 539 },
589 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 540 },
590 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 541 },
591 .{ .char = 'b', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
592 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 438 },
593 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 542 },
594 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 543 },
595 .{ .char = 'b', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
596 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 544 },
597 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 545 },
598 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 546 },
599 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
600 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 389, .child_index = 547 },
601 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 419 },
602 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 548 },
603 .{ .char = 'v', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 549 },
604 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 550 },
605 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 540 },
606 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 108, .child_index = 551 },
607 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 540 },
608 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 552 },
609 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 553 },
610 .{ .char = 'e', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
611 .{ .char = 'i', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
612 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 554 },
613 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 555 },
614 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 556 },
615 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 557 },
616 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 558 },
617 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 559 },
618 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 560 },
619 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 561 },
620 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 563 },
621 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 563 },
622 .{ .char = 'j', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 566 },
623 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 567 },
624 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 568 },
625 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 361 },
626 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
627 .{ .char = 'h', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 361 },
628 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
629 .{ .char = 'y', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
630 .{ .char = 'o', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
631 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 569 },
632 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 570 },
633 .{ .char = '1', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
634 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 571 },
635 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
636 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
637 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
638 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
639 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
640 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 573 },
641 .{ .char = 'b', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
642 .{ .char = 'x', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
643 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 574 },
644 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 575 },
645 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 576 },
646 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 577 },
647 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 238 },
648 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 578 },
649 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 579 },
650 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 580 },
651 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 581 },
652 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 582 },
653 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 579 },
654 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 583 },
655 .{ .char = '0', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 361 },
656 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
657 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 322 },
658 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 584 },
659 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 292 },
660 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 585 },
661 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 291 },
662 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 450 },
663 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 586 },
664 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 292 },
665 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
666 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 587 },
667 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 588 },
668 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 589 },
669 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
670 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 590 },
671 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 591 },
672 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 592 },
673 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 595 },
674 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 596 },
675 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
676 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
677 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 282 },
678 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 217 },
679 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 598 },
680 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 585 },
681 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 291 },
682 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 450 },
683 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 600 },
684 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
685 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 601 },
686 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 602 },
687 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
688 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 604 },
689 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 505 },
690 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 393 },
691 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 607 },
692 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 457 },
693 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
694 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 608 },
695 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 613 },
696 .{ .char = 'c', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
697 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 292 },
698 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 458 },
699 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 614 },
700 .{ .char = 'k', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
701 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 585 },
702 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
703 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 497 },
704 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 615 },
705 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 484 },
706 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 618 },
707 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 29, .child_index = 619 },
708 .{ .char = 'F', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 620 },
709 .{ .char = 'T', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 621 },
710 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 622 },
711 .{ .char = 'E', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 623 },
712 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 624 },
713 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 625 },
714 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 626 },
715 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 30, .child_index = 627 },
716 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2967, .child_index = 628 },
717 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 17, .child_index = 629 },
718 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 630 },
719 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 631 },
720 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 632 },
721 .{ .char = '1', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 633 },
722 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 634 },
723 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 635 },
724 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 636 },
725 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 637 },
726 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 389, .child_index = 638 },
727 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 569 },
728 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
729 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 499 },
730 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 108, .child_index = 639 },
731 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 520 },
732 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 641 },
733 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 642 },
734 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 458 },
735 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 643 },
736 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 644 },
737 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 645 },
738 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 646 },
739 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 647 },
740 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
741 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
742 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 648 },
743 .{ .char = '6', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 649 },
744 .{ .char = '8', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
745 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 650 },
746 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 651 },
747 .{ .char = 'a', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
748 .{ .char = 'c', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
749 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 652 },
750 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
751 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
752 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 653 },
753 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 654 },
754 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 568 },
755 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 521 },
756 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
757 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 656 },
758 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
759 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
760 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
761 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
762 .{ .char = 'a', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
763 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 657 },
764 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
765 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
766 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 658 },
767 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 659 },
768 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 660 },
769 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 661 },
770 .{ .char = 'o', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
771 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 662 },
772 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
773 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
774 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 463 },
775 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 206 },
776 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 361 },
777 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 663 },
778 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
779 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
780 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 664 },
781 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 311 },
782 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 450 },
783 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 598 },
784 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 291 },
785 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 450 },
786 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
787 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
788 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
789 .{ .char = 'k', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
790 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 665 },
791 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 667 },
792 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 654 },
793 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 286 },
794 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 585 },
795 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 291 },
796 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 450 },
797 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 668 },
798 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 29, .child_index = 669 },
799 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 670 },
800 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 671 },
801 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 672 },
802 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 673 },
803 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 674 },
804 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 675 },
805 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
806 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 30, .child_index = 676 },
807 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2967, .child_index = 677 },
808 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 17, .child_index = 678 },
809 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 679 },
810 .{ .char = 'i', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 680 },
811 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 681 },
812 .{ .char = '0', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 680 },
813 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 682 },
814 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 683 },
815 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 458 },
816 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 684 },
817 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 389, .child_index = 686 },
818 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 107, .child_index = 701 },
819 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 710 },
820 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 711 },
821 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 712 },
822 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 714 },
823 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 715 },
824 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 716 },
825 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 717 },
826 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 718 },
827 .{ .char = '6', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
828 .{ .char = '4', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
829 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 719 },
830 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 720 },
831 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 206 },
832 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 721 },
833 .{ .char = 'm', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
834 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
835 .{ .char = 'h', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
836 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
837 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 353 },
838 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 722 },
839 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 723 },
840 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 722 },
841 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 724 },
842 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 524 },
843 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
844 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
845 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
846 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 549 },
847 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 725 },
848 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 29, .child_index = 726 },
849 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 727 },
850 .{ .char = 'C', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 728 },
851 .{ .char = 'A', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 729 },
852 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 730 },
853 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 731 },
854 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 732 },
855 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 30, .child_index = 733 },
856 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2967, .child_index = 734 },
857 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 17, .child_index = 735 },
858 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 736 },
859 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
860 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 737 },
861 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 738 },
862 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 739 },
863 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 648 },
864 .{ .char = '6', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 649 },
865 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 48, .child_index = 740 },
866 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 742 },
867 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 744 },
868 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 40, .child_index = 746 },
869 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 748 },
870 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 58, .child_index = 749 },
871 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 753 },
872 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 84, .child_index = 755 },
873 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 23, .child_index = 759 },
874 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 761 },
875 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 53, .child_index = 762 },
876 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 29, .child_index = 766 },
877 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 770 },
878 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 771 },
879 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 773 },
880 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 774 },
881 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 776 },
882 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 40, .child_index = 777 },
883 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 778 },
884 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 779 },
885 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 780 },
886 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 13, .child_index = 781 },
887 .{ .char = 'v', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 784 },
888 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 785 },
889 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 786 },
890 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 787 },
891 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 788 },
892 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 789 },
893 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 790 },
894 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 8, .child_index = 791 },
895 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 793 },
896 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 794 },
897 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 795 },
898 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 463 },
899 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 796 },
900 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 797 },
901 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 456 },
902 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 798 },
903 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 206 },
904 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 799 },
905 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 29, .child_index = 800 },
906 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 671 },
907 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 801 },
908 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 802 },
909 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 803 },
910 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 804 },
911 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 805 },
912 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 30, .child_index = 806 },
913 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2967, .child_index = 818 },
914 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 17, .child_index = 819 },
915 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 820 },
916 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 821 },
917 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
918 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 822 },
919 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 823 },
920 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 36, .child_index = 824 },
921 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 825 },
922 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 826 },
923 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 827 },
924 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 828 },
925 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 26, .child_index = 830 },
926 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 834 },
927 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 835 },
928 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 34, .child_index = 836 },
929 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 840 },
930 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 841 },
931 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 842 },
932 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 844 },
933 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 846 },
934 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 72, .child_index = 847 },
935 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 835 },
936 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 849 },
937 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 850 },
938 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 851 },
939 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 852 },
940 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 853 },
941 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 14, .child_index = 854 },
942 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 33, .child_index = 855 },
943 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 856 },
944 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 857 },
945 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 858 },
946 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 860 },
947 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 861 },
948 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 862 },
949 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 863 },
950 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 849 },
951 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 864 },
952 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 865 },
953 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 866 },
954 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 866 },
955 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 867 },
956 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 40, .child_index = 868 },
957 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 869 },
958 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 870 },
959 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 871 },
960 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 872 },
961 .{ .char = 'w', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 873 },
962 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 874 },
963 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 875 },
964 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 780 },
965 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 876 },
966 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 877 },
967 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 878 },
968 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 879 },
969 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 880 },
970 .{ .char = '6', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 649 },
971 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 881 },
972 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 882 },
973 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 883 },
974 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 884 },
975 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 203 },
976 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
977 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 322 },
978 .{ .char = 'j', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 885 },
979 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 29, .child_index = 886 },
980 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 887 },
981 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 888 },
982 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 889 },
983 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 890 },
984 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 891 },
985 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 892 },
986 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 895 },
987 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 897 },
988 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 898 },
989 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 899 },
990 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 900 },
991 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 901 },
992 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 903 },
993 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 904 },
994 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 905 },
995 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 908 },
996 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 910 },
997 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2967, .child_index = 911 },
998 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 17, .child_index = 932 },
999 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 933 },
1000 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 934 },
1001 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 935 },
1002 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 936 },
1003 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 36, .child_index = 937 },
1004 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 938 },
1005 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 940 },
1006 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 941 },
1007 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 942 },
1008 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 943 },
1009 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 944 },
1010 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 945 },
1011 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 946 },
1012 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 947 },
1013 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 949 },
1014 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 950 },
1015 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 951 },
1016 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 944 },
1017 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 952 },
1018 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 953 },
1019 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 955 },
1020 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 956 },
1021 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 15, .child_index = 957 },
1022 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 959 },
1023 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 960 },
1024 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 960 },
1025 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 961 },
1026 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 36, .child_index = 962 },
1027 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 36, .child_index = 962 },
1028 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 844 },
1029 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 963 },
1030 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 964 },
1031 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 967 },
1032 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
1033 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 970 },
1034 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 971 },
1035 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 972 },
1036 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 973 },
1037 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 974 },
1038 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 975 },
1039 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 976 },
1040 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 943 },
1041 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 977 },
1042 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 978 },
1043 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 849 },
1044 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 979 },
1045 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 871 },
1046 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 875 },
1047 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 40, .child_index = 980 },
1048 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 981 },
1049 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 866 },
1050 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 982 },
1051 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 871 },
1052 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 983 },
1053 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 984 },
1054 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 985 },
1055 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 986 },
1056 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 987 },
1057 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 988 },
1058 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 989 },
1059 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 990 },
1060 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 991 },
1061 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 992 },
1062 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 993 },
1063 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 994 },
1064 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 995 },
1065 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 29, .child_index = 996 },
1066 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 997 },
1067 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 998 },
1068 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 999 },
1069 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
1070 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1000 },
1071 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1001 },
1072 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1002 },
1073 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1001 },
1074 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1003 },
1075 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1004 },
1076 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1005 },
1077 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1006 },
1078 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1007 },
1079 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1008 },
1080 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1009 },
1081 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1010 },
1082 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1011 },
1083 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1012 },
1084 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1013 },
1085 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1014 },
1086 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1015 },
1087 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1016 },
1088 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1017 },
1089 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 904 },
1090 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 28, .child_index = 1018 },
1091 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 302, .child_index = 1019 },
1092 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 11, .child_index = 1028 },
1093 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 114, .child_index = 1032 },
1094 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 1044 },
1095 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 58, .child_index = 1049 },
1096 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 49, .child_index = 1053 },
1097 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1061 },
1098 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 1062 },
1099 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 27, .child_index = 1064 },
1100 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 52, .child_index = 1068 },
1101 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 686, .child_index = 1074 },
1102 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 25, .child_index = 1080 },
1103 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 1083 },
1104 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 142, .child_index = 1086 },
1105 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 52, .child_index = 1091 },
1106 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 71, .child_index = 1095 },
1107 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 19, .child_index = 1107 },
1108 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 13, .child_index = 1111 },
1109 .{ .char = 'v', .end_of_word = false, .end_of_list = false, .number = 1273, .child_index = 1115 },
1110 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 22, .child_index = 1120 },
1111 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 17, .child_index = 1123 },
1112 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1124 },
1113 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 521 },
1114 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1125 },
1115 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 1126 },
1116 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 36, .child_index = 1127 },
1117 .{ .char = '0', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1128 },
1118 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1129 },
1119 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1130 },
1120 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1131 },
1121 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1132 },
1122 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1133 },
1123 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1134 },
1124 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1135 },
1125 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 960 },
1126 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 960 },
1127 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 946 },
1128 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 1138 },
1129 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1140 },
1130 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1141 },
1131 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 944 },
1132 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 944 },
1133 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 952 },
1134 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1131 },
1135 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1142 },
1136 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 1126 },
1137 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1131 },
1138 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1131 },
1139 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1143 },
1140 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1144 },
1141 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 36, .child_index = 1145 },
1142 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1153 },
1143 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1154 },
1144 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 292 },
1145 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 486 },
1146 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1155 },
1147 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 1126 },
1148 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1156 },
1149 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 1157 },
1150 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 1159 },
1151 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1160 },
1152 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1161 },
1153 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1162 },
1154 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1164 },
1155 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1165 },
1156 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 949 },
1157 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1166 },
1158 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1167 },
1159 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 40, .child_index = 1168 },
1160 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 1169 },
1161 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1170 },
1162 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 1171 },
1163 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1172 },
1164 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1173 },
1165 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1174 },
1166 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1175 },
1167 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1176 },
1168 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1177 },
1169 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1178 },
1170 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1179 },
1171 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1182 },
1172 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1185 },
1173 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 1187 },
1174 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1188 },
1175 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 29, .child_index = 1189 },
1176 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1196 },
1177 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1197 },
1178 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1198 },
1179 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1199 },
1180 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1012 },
1181 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1200 },
1182 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1201 },
1183 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1202 },
1184 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1203 },
1185 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1204 },
1186 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1205 },
1187 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1206 },
1188 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1012 },
1189 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1012 },
1190 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1001 },
1191 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1207 },
1192 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1208 },
1193 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1209 },
1194 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1012 },
1195 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1210 },
1196 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1211 },
1197 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 28, .child_index = 1212 },
1198 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 135 },
1199 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 1221 },
1200 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 1222 },
1201 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 1223 },
1202 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 122, .child_index = 1225 },
1203 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 403 },
1204 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 134, .child_index = 1226 },
1205 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 11, .child_index = 1227 },
1206 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 1229 },
1207 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 142 },
1208 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1230 },
1209 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1231 },
1210 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 144 },
1211 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 30, .child_index = 1232 },
1212 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1239 },
1213 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 137 },
1214 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 1240 },
1215 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1242 },
1216 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 154 },
1217 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 11, .child_index = 1243 },
1218 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 20, .child_index = 1247 },
1219 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 1251 },
1220 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 161 },
1221 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 162 },
1222 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 1254 },
1223 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1256 },
1224 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1257 },
1225 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1258 },
1226 .{ .char = 'w', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1259 },
1227 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1260 },
1228 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1261 },
1229 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 25, .child_index = 1262 },
1230 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 1263 },
1231 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 23, .child_index = 1264 },
1232 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1266 },
1233 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1267 },
1234 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1268 },
1235 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 1269 },
1236 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 20, .child_index = 1271 },
1237 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1274 },
1238 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 1276 },
1239 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 178 },
1240 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1279 },
1241 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1280 },
1242 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1281 },
1243 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1282 },
1244 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1283 },
1245 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 1284 },
1246 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 13, .child_index = 1287 },
1247 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1294 },
1248 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1296 },
1249 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1297 },
1250 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 1298 },
1251 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 1300 },
1252 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1302 },
1253 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1304 },
1254 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 1306 },
1255 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 135, .child_index = 1307 },
1256 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1308 },
1257 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 534, .child_index = 1309 },
1258 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1310 },
1259 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 1311 },
1260 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 1312 },
1261 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1314 },
1262 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1315 },
1263 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1316 },
1264 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1317 },
1265 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1318 },
1266 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 11, .child_index = 1320 },
1267 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 108, .child_index = 1322 },
1268 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1323 },
1269 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 1325 },
1270 .{ .char = '6', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 1326 },
1271 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 19, .child_index = 1327 },
1272 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 1331 },
1273 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 1332 },
1274 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1334 },
1275 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 1335 },
1276 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1336 },
1277 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1337 },
1278 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 1338 },
1279 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1340 },
1280 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 220 },
1281 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1341 },
1282 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1343 },
1283 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1344 },
1284 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 20, .child_index = 1346 },
1285 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1349 },
1286 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 1350 },
1287 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1297 },
1288 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1351 },
1289 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1352 },
1290 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1334 },
1291 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1340 },
1292 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1354 },
1293 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1357 },
1294 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 227 },
1295 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1263, .child_index = 1358 },
1296 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1359 },
1297 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 176 },
1298 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 231 },
1299 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 14, .child_index = 1361 },
1300 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 235 },
1301 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 236 },
1302 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 17, .child_index = 1362 },
1303 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
1304 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1363 },
1305 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 1364 },
1306 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 36, .child_index = 1368 },
1307 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1376 },
1308 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1379 },
1309 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1380 },
1310 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1381 },
1311 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1383 },
1312 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1384 },
1313 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1385 },
1314 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1389 },
1315 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 451 },
1316 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1390 },
1317 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1384 },
1318 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 1364 },
1319 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1394 },
1320 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1395 },
1321 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1131 },
1322 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1390 },
1323 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1396 },
1324 .{ .char = 'c', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1397 },
1325 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1399 },
1326 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1397 },
1327 .{ .char = 'h', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1399 },
1328 .{ .char = 'i', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1397 },
1329 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 1400 },
1330 .{ .char = 's', .end_of_word = true, .end_of_list = false, .number = 6, .child_index = 1402 },
1331 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 13, .child_index = 1405 },
1332 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1409 },
1333 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1410 },
1334 .{ .char = '4', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 974 },
1335 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1411 },
1336 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1412 },
1337 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 1364 },
1338 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 1413 },
1339 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1131 },
1340 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 950 },
1341 .{ .char = 'i', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1342 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1389 },
1343 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1414 },
1344 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1415 },
1345 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1131 },
1346 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1419 },
1347 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 40, .child_index = 1422 },
1348 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 1423 },
1349 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1425 },
1350 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1426 },
1351 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1430 },
1352 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1431 },
1353 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 344 },
1354 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1432 },
1355 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1433 },
1356 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1434 },
1357 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1435 },
1358 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1436 },
1359 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1437 },
1360 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1438 },
1361 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1439 },
1362 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1440 },
1363 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1441 },
1364 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1442 },
1365 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1443 },
1366 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 1444 },
1367 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1445 },
1368 .{ .char = 'A', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1446 },
1369 .{ .char = 'C', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 1447 },
1370 .{ .char = 'D', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1448 },
1371 .{ .char = 'E', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 1449 },
1372 .{ .char = 'I', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1450 },
1373 .{ .char = 'O', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1451 },
1374 .{ .char = 'X', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1452 },
1375 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1453 },
1376 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 344 },
1377 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1454 },
1378 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1455 },
1379 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1456 },
1380 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
1381 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1457 },
1382 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1458 },
1383 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1459 },
1384 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1460 },
1385 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1461 },
1386 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1462 },
1387 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1463 },
1388 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1464 },
1389 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1465 },
1390 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1466 },
1391 .{ .char = 'C', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1467 },
1392 .{ .char = 'N', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1468 },
1393 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1469 },
1394 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1470 },
1395 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1471 },
1396 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1472 },
1397 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1473 },
1398 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 1474 },
1399 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1477 },
1400 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1480 },
1401 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1481 },
1402 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1483 },
1403 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1484 },
1404 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 122, .child_index = 1485 },
1405 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 134, .child_index = 1486 },
1406 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 1350 },
1407 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1487 },
1408 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 1488 },
1409 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1489 },
1410 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1490 },
1411 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 294 },
1412 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 137 },
1413 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1491 },
1414 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1492 },
1415 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 296 },
1416 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 140 },
1417 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 164 },
1418 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1493 },
1419 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1494 },
1420 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 299 },
1421 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1495 },
1422 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1496 },
1423 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 296 },
1424 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1497 },
1425 .{ .char = 'z', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1498 },
1426 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1500 },
1427 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1501 },
1428 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1504 },
1429 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 9, .child_index = 1505 },
1430 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 209 },
1431 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 306 },
1432 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1508 },
1433 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 223 },
1434 .{ .char = 'z', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1498 },
1435 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
1436 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1509 },
1437 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1510 },
1438 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1511 },
1439 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1512 },
1440 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1513 },
1441 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 25, .child_index = 1514 },
1442 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 8, .child_index = 1515 },
1443 .{ .char = 'p', .end_of_word = true, .end_of_list = false, .number = 21, .child_index = 1518 },
1444 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1524 },
1445 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1526 },
1446 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1527 },
1447 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 1528 },
1448 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1529 },
1449 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1530 },
1450 .{ .char = 'a', .end_of_word = true, .end_of_list = false, .number = 10, .child_index = 1531 },
1451 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1534 },
1452 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1535 },
1453 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1536 },
1454 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 210 },
1455 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1537 },
1456 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 1538 },
1457 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1540 },
1458 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1541 },
1459 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1543 },
1460 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1544 },
1461 .{ .char = '3', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1545 },
1462 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1546 },
1463 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 332 },
1464 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 5, .child_index = 1547 },
1465 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1549 },
1466 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1550 },
1467 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1551 },
1468 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1553 },
1469 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1554 },
1470 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1555 },
1471 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1556 },
1472 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1558 },
1473 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 344 },
1474 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1559 },
1475 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1560 },
1476 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1561 },
1477 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 194 },
1478 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1302 },
1479 .{ .char = 'g', .end_of_word = true, .end_of_list = false, .number = 23, .child_index = 1562 },
1480 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 352 },
1481 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1567 },
1482 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1568 },
1483 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 295 },
1484 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1569 },
1485 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1570 },
1486 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 135, .child_index = 1574 },
1487 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1575 },
1488 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 534, .child_index = 1576 },
1489 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1577 },
1490 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 10, .child_index = 1578 },
1491 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1581 },
1492 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1582 },
1493 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1583 },
1494 .{ .char = 'j', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1585 },
1495 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1587 },
1496 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1588 },
1497 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1589 },
1498 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1590 },
1499 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1591 },
1500 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 8, .child_index = 1592 },
1501 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 108, .child_index = 1595 },
1502 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1596 },
1503 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 365 },
1504 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 1598 },
1505 .{ .char = '0', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 1599 },
1506 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1600 },
1507 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 1602 },
1508 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 1603 },
1509 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1605 },
1510 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1606 },
1511 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 1608 },
1512 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 1609 },
1513 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1610 },
1514 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 1611 },
1515 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1613 },
1516 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1618 },
1517 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1619 },
1518 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 9, .child_index = 1505 },
1519 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1620 },
1520 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1621 },
1521 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 210 },
1522 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1622 },
1523 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 327 },
1524 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1623 },
1525 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1624 },
1526 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 377 },
1527 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 17, .child_index = 1625 },
1528 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1481 },
1529 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 8, .child_index = 1632 },
1530 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1635 },
1531 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 291 },
1532 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1636 },
1533 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1637 },
1534 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1639 },
1535 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1640 },
1536 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1623 },
1537 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1263, .child_index = 1641 },
1538 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 176 },
1539 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 178 },
1540 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 1642 },
1541 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 17, .child_index = 1643 },
1542 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1650 },
1543 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1131 },
1544 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1131 },
1545 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1131 },
1546 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1131 },
1547 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 1651 },
1548 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1653 },
1549 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1654 },
1550 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1655 },
1551 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 1656 },
1552 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1658 },
1553 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1659 },
1554 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1660 },
1555 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 519 },
1556 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 585 },
1557 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1662 },
1558 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1663 },
1559 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1664 },
1560 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1561 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1665 },
1562 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1666 },
1563 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1667 },
1564 .{ .char = 'm', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1668 },
1565 .{ .char = 'n', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1668 },
1566 .{ .char = 'p', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1668 },
1567 .{ .char = 'z', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1668 },
1568 .{ .char = 'i', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1569 .{ .char = 'm', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1570 .{ .char = 'n', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1571 .{ .char = 'p', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1572 .{ .char = 'z', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1573 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1669 },
1574 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1668 },
1575 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1670 },
1576 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1577 .{ .char = '4', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1578 .{ .char = '2', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1579 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1580 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1399 },
1581 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1582 .{ .char = '4', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1583 .{ .char = 'c', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 1397 },
1584 .{ .char = 'c', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1397 },
1585 .{ .char = 'i', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1397 },
1586 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 1400 },
1587 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 1397 },
1588 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1671 },
1589 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1672 },
1590 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1673 },
1591 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1676 },
1592 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 1677 },
1593 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1678 },
1594 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1679 },
1595 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1680 },
1596 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1681 },
1597 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1682 },
1598 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1683 },
1599 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1685 },
1600 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1686 },
1601 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 40, .child_index = 1687 },
1602 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 1688 },
1603 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1689 },
1604 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1690 },
1605 .{ .char = '1', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1691 },
1606 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1607 .{ .char = '4', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1608 .{ .char = '8', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1609 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1692 },
1610 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1693 },
1611 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1694 },
1612 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1434 },
1613 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1695 },
1614 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1696 },
1615 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1697 },
1616 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1698 },
1617 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1699 },
1618 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1700 },
1619 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1701 },
1620 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1702 },
1621 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1703 },
1622 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1704 },
1623 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 1705 },
1624 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1706 },
1625 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1708 },
1626 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1709 },
1627 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1710 },
1628 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 1711 },
1629 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1710 },
1630 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 1712 },
1631 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1451 },
1632 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1714 },
1633 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1715 },
1634 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1716 },
1635 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 899 },
1636 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1717 },
1637 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1718 },
1638 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1719 },
1639 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1720 },
1640 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
1641 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1721 },
1642 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1722 },
1643 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1461 },
1644 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1723 },
1645 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1724 },
1646 .{ .char = 'F', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1725 },
1647 .{ .char = 'S', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1725 },
1648 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 409 },
1649 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1473 },
1650 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1726 },
1651 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1727 },
1652 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1728 },
1653 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1470 },
1654 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1473 },
1655 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1729 },
1656 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1470 },
1657 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1473 },
1658 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1731 },
1659 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 8, .child_index = 1632 },
1660 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1733 },
1661 .{ .char = 'c', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1734 },
1662 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1737 },
1663 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1738 },
1664 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 122, .child_index = 1739 },
1665 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 134, .child_index = 1740 },
1666 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1756 },
1667 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 12, .child_index = 1757 },
1668 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1761 },
1669 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1762 },
1670 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1763 },
1671 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1765 },
1672 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
1673 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
1674 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1768 },
1675 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1769 },
1676 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1770 },
1677 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 549 },
1678 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1679 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1771 },
1680 .{ .char = 'j', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 361 },
1681 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1772 },
1682 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1773 },
1683 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1774 },
1684 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1775 },
1685 .{ .char = 'h', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 1766 },
1686 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1687 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1776 },
1688 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1778 },
1689 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1779 },
1690 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1780 },
1691 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1781 },
1692 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1782 },
1693 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 25, .child_index = 1783 },
1694 .{ .char = 'c', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 1766 },
1695 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1784 },
1696 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1697 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1785 },
1698 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 5, .child_index = 1547 },
1699 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1786 },
1700 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1775 },
1701 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1702 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1787 },
1703 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1788 },
1704 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1789 },
1705 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
1706 .{ .char = 'm', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
1707 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 549 },
1708 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1790 },
1709 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1791 },
1710 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1775 },
1711 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1712 .{ .char = 'x', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
1713 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
1714 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
1715 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1792 },
1716 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1793 },
1717 .{ .char = 'e', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1718 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1794 },
1719 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1795 },
1720 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 458 },
1721 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 344 },
1722 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1796 },
1723 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1493 },
1724 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1797 },
1725 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1798 },
1726 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1775 },
1727 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1728 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1799 },
1729 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1800 },
1730 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1801 },
1731 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1802 },
1732 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1803 },
1733 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1804 },
1734 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1805 },
1735 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 457 },
1736 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1806 },
1737 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1807 },
1738 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1808 },
1739 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1794 },
1740 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1809 },
1741 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 1810 },
1742 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 5, .child_index = 1547 },
1743 .{ .char = 'b', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 1766 },
1744 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1775 },
1745 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1746 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1493 },
1747 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1812 },
1748 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1813 },
1749 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1814 },
1750 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 484 },
1751 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 485 },
1752 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1817 },
1753 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 135, .child_index = 1818 },
1754 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
1755 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 534, .child_index = 1819 },
1756 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1733 },
1757 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1775 },
1758 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1759 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
1760 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1834 },
1761 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1835 },
1762 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1837 },
1763 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1838 },
1764 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1839 },
1765 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1840 },
1766 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1841 },
1767 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1842 },
1768 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1843 },
1769 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1844 },
1770 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1845 },
1771 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1775 },
1772 .{ .char = 'i', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 361 },
1773 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1774 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 108, .child_index = 1846 },
1775 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1462 },
1776 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1859 },
1777 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 1860 },
1778 .{ .char = '0', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 1863 },
1779 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1864 },
1780 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 295 },
1781 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 7, .child_index = 1866 },
1782 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1867 },
1783 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1868 },
1784 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1869 },
1785 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 332 },
1786 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
1787 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1870 },
1788 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 1871 },
1789 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1872 },
1790 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 1874 },
1791 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
1792 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1875 },
1793 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1876 },
1794 .{ .char = 'j', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 497 },
1795 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 344 },
1796 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 519 },
1797 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1877 },
1798 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1878 },
1799 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1872 },
1800 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1879 },
1801 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
1802 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1872 },
1803 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1880 },
1804 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 500 },
1805 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 505 },
1806 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 323 },
1807 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 509 },
1808 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 511 },
1809 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 512 },
1810 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 513 },
1811 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1784 },
1812 .{ .char = 'h', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 1766 },
1813 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1814 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1881 },
1815 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1882 },
1816 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1883 },
1817 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1884 },
1818 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1885 },
1819 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1886 },
1820 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1263, .child_index = 1887 },
1821 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 1888 },
1822 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1889 },
1823 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1890 },
1824 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 898 },
1825 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1891 },
1826 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1893 },
1827 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1894 },
1828 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1896 },
1829 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1897 },
1830 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 1898 },
1831 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1899 },
1832 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1900 },
1833 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1901 },
1834 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1901 },
1835 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 1902 },
1836 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1903 },
1837 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1904 },
1838 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1905 },
1839 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1906 },
1840 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1658 },
1841 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1907 },
1842 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 569 },
1843 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1908 },
1844 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1909 },
1845 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1910 },
1846 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1911 },
1847 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1912 },
1848 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1913 },
1849 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1914 },
1850 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 458 },
1851 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1915 },
1852 .{ .char = 'i', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1853 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 655 },
1854 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1918 },
1855 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1920 },
1856 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 1921 },
1857 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1922 },
1858 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1923 },
1859 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1924 },
1860 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1925 },
1861 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1926 },
1862 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 655 },
1863 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 450 },
1864 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1927 },
1865 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1389 },
1866 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 40, .child_index = 1928 },
1867 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1929 },
1868 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1930 },
1869 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1931 },
1870 .{ .char = '6', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1871 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1932 },
1872 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1933 },
1873 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1934 },
1874 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1935 },
1875 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1936 },
1876 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1937 },
1877 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1438 },
1878 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1938 },
1879 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1939 },
1880 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1940 },
1881 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 286 },
1882 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
1883 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 451 },
1884 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 1941 },
1885 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1942 },
1886 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1943 },
1887 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 1712 },
1888 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1944 },
1889 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1945 },
1890 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 1946 },
1891 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 648 },
1892 .{ .char = '8', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1893 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1947 },
1894 .{ .char = 'I', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1443 },
1895 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1948 },
1896 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1949 },
1897 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1950 },
1898 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 1951 },
1899 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1957 },
1900 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1958 },
1901 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1199 },
1902 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1959 },
1903 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1199 },
1904 .{ .char = 'S', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1960 },
1905 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1961 },
1906 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1962 },
1907 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1966 },
1908 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 1967 },
1909 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 1969 },
1910 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1470 },
1911 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1473 },
1912 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1972 },
1913 .{ .char = 'b', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
1914 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 549 },
1915 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1916 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1973 },
1917 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1974 },
1918 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 122, .child_index = 1975 },
1919 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 11, .child_index = 1976 },
1920 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1979 },
1921 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1982 },
1922 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1983 },
1923 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 1984 },
1924 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 1985 },
1925 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 420 },
1926 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1987 },
1927 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 1988 },
1928 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 1991 },
1929 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 51, .child_index = 1993 },
1930 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2000 },
1931 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 2003 },
1932 .{ .char = 'v', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2008 },
1933 .{ .char = 'w', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 2009 },
1934 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 274 },
1935 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2011 },
1936 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 1766 },
1937 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1784 },
1938 .{ .char = 'h', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 1766 },
1939 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1940 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 2012 },
1941 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2013 },
1942 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2016 },
1943 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 569 },
1944 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2017 },
1945 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1784 },
1946 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
1947 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2018 },
1948 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2019 },
1949 .{ .char = 'b', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 1528 },
1950 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 332 },
1951 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2020 },
1952 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2021 },
1953 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 2022 },
1954 .{ .char = '1', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2023 },
1955 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2025 },
1956 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2027 },
1957 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2028 },
1958 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2029 },
1959 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2030 },
1960 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2031 },
1961 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2032 },
1962 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 25, .child_index = 2033 },
1963 .{ .char = '1', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2034 },
1964 .{ .char = '0', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
1965 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2035 },
1966 .{ .char = '1', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
1967 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2036 },
1968 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2037 },
1969 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
1970 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2038 },
1971 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2039 },
1972 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2040 },
1973 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
1974 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2041 },
1975 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 2042 },
1976 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2043 },
1977 .{ .char = 'b', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
1978 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2044 },
1979 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2045 },
1980 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 328 },
1981 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2046 },
1982 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2047 },
1983 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 2048 },
1984 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2049 },
1985 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2050 },
1986 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2051 },
1987 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 579 },
1988 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2052 },
1989 .{ .char = '0', .end_of_word = true, .end_of_list = false, .number = 5, .child_index = 1547 },
1990 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
1991 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2053 },
1992 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2054 },
1993 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 585 },
1994 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 291 },
1995 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2055 },
1996 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2056 },
1997 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 135, .child_index = 2057 },
1998 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 50, .child_index = 2069 },
1999 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 56, .child_index = 2073 },
2000 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 50, .child_index = 2079 },
2001 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 26, .child_index = 2084 },
2002 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 106, .child_index = 2087 },
2003 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 2098 },
2004 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 2100 },
2005 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 2102 },
2006 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 73, .child_index = 2103 },
2007 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 2108 },
2008 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2110 },
2009 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 2111 },
2010 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 97, .child_index = 2112 },
2011 .{ .char = 'v', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2119 },
2012 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2120 },
2013 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2121 },
2014 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2122 },
2015 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2123 },
2016 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2124 },
2017 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2125 },
2018 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2126 },
2019 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2127 },
2020 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2128 },
2021 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2129 },
2022 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2130 },
2023 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2131 },
2024 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2132 },
2025 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2133 },
2026 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2134 },
2027 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2136 },
2028 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2137 },
2029 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 41, .child_index = 2138 },
2030 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2144 },
2031 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2145 },
2032 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 2147 },
2033 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 19, .child_index = 2150 },
2034 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2155 },
2035 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2156 },
2036 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 2160 },
2037 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2163 },
2038 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2166 },
2039 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 2167 },
2040 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2168 },
2041 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2169 },
2042 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 2170 },
2043 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2172 },
2044 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1876 },
2045 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 7, .child_index = 2173 },
2046 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2174 },
2047 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2175 },
2048 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2176 },
2049 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2177 },
2050 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 10, .child_index = 2178 },
2051 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1733 },
2052 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2181 },
2053 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2183 },
2054 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2185 },
2055 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 654 },
2056 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2186 },
2057 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2187 },
2058 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2188 },
2059 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2189 },
2060 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2036 },
2061 .{ .char = 'c', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 1547 },
2062 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1589 },
2063 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2190 },
2064 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2191 },
2065 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2192 },
2066 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1263, .child_index = 2193 },
2067 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 2194 },
2068 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2196 },
2069 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2197 },
2070 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 238 },
2071 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1007 },
2072 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2198 },
2073 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1013 },
2074 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2199 },
2075 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1017 },
2076 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2200 },
2077 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2202 },
2078 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1904 },
2079 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1904 },
2080 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2203 },
2081 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2204 },
2082 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2204 },
2083 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2205 },
2084 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1904 },
2085 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2206 },
2086 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 569 },
2087 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2207 },
2088 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2211 },
2089 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2212 },
2090 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2213 },
2091 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2214 },
2092 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2215 },
2093 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2216 },
2094 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2217 },
2095 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 655 },
2096 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2218 },
2097 .{ .char = 'i', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
2098 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
2099 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2219 },
2100 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 2220 },
2101 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1131 },
2102 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2221 },
2103 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2222 },
2104 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1926 },
2105 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2223 },
2106 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2225 },
2107 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 40, .child_index = 2226 },
2108 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2227 },
2109 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2228 },
2110 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2229 },
2111 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2230 },
2112 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2231 },
2113 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2232 },
2114 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 580 },
2115 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2233 },
2116 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2234 },
2117 .{ .char = '6', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 649 },
2118 .{ .char = '6', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 649 },
2119 .{ .char = 'g', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2120 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 2235 },
2121 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2236 },
2122 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2237 },
2123 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2238 },
2124 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2239 },
2125 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 2240 },
2126 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2241 },
2127 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 582 },
2128 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2242 },
2129 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1464 },
2130 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2243 },
2131 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2245 },
2132 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2247 },
2133 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 585 },
2134 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2248 },
2135 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 664 },
2136 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2249 },
2137 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 656 },
2138 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2250 },
2139 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2251 },
2140 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2252 },
2141 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2253 },
2142 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2255 },
2143 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2256 },
2144 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2257 },
2145 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2258 },
2146 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2259 },
2147 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2256 },
2148 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2260 },
2149 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2262 },
2150 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2262 },
2151 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2263 },
2152 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2264 },
2153 .{ .char = 'a', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 2266 },
2154 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 122, .child_index = 2267 },
2155 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2268 },
2156 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 2269 },
2157 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2272 },
2158 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1940 },
2159 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 412 },
2160 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 412 },
2161 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2273 },
2162 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 412 },
2163 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 7, .child_index = 2274 },
2164 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2277 },
2165 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2278 },
2166 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2280 },
2167 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2281 },
2168 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2283 },
2169 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2284 },
2170 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2286 },
2171 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2287 },
2172 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2288 },
2173 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2290 },
2174 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2293 },
2175 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 2295 },
2176 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 2297 },
2177 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 2299 },
2178 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2302 },
2179 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2303 },
2180 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 520 },
2181 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2305 },
2182 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2288 },
2183 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2293 },
2184 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2293 },
2185 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 2306 },
2186 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2302 },
2187 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2308 },
2188 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 431 },
2189 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2287 },
2190 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 2309 },
2191 .{ .char = 'v', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 2310 },
2192 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 648 },
2193 .{ .char = '3', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2311 },
2194 .{ .char = '6', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 649 },
2195 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2312 },
2196 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2313 },
2197 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2314 },
2198 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2315 },
2199 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2316 },
2200 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2317 },
2201 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 2318 },
2202 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2319 },
2203 .{ .char = '6', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2204 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 238 },
2205 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2206 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2320 },
2207 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2321 },
2208 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2322 },
2209 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2323 },
2210 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2325 },
2211 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2326 },
2212 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 25, .child_index = 2327 },
2213 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2319 },
2214 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 2328 },
2215 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2329 },
2216 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2330 },
2217 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2331 },
2218 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2332 },
2219 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2333 },
2220 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2334 },
2221 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 2335 },
2222 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2336 },
2223 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2337 },
2224 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2338 },
2225 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2339 },
2226 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2340 },
2227 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2236 },
2228 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 2341 },
2229 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2343 },
2230 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2344 },
2231 .{ .char = 'a', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
2232 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
2233 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2345 },
2234 .{ .char = 'y', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 2346 },
2235 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 2346 },
2236 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 19, .child_index = 2347 },
2237 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2350 },
2238 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 2353 },
2239 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 2354 },
2240 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2355 },
2241 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2356 },
2242 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2357 },
2243 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 2360 },
2244 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 21, .child_index = 2365 },
2245 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2368 },
2246 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 25, .child_index = 2371 },
2247 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2373 },
2248 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 2374 },
2249 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2375 },
2250 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2376 },
2251 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 2377 },
2252 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2378 },
2253 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 2379 },
2254 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2380 },
2255 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 13, .child_index = 2382 },
2256 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 2384 },
2257 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 2385 },
2258 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2386 },
2259 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2387 },
2260 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 32, .child_index = 2388 },
2261 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2390 },
2262 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2387 },
2263 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2391 },
2264 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2392 },
2265 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 2098 },
2266 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2393 },
2267 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 2394 },
2268 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2400 },
2269 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2401 },
2270 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2402 },
2271 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2404 },
2272 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2405 },
2273 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 14, .child_index = 2406 },
2274 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2410 },
2275 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 26, .child_index = 2413 },
2276 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 2420 },
2277 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2423 },
2278 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2424 },
2279 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 2425 },
2280 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2426 },
2281 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 2427 },
2282 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 28, .child_index = 2430 },
2283 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 20, .child_index = 2432 },
2284 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 2433 },
2285 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2435 },
2286 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2436 },
2287 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2437 },
2288 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2110 },
2289 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2439 },
2290 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 2441 },
2291 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2443 },
2292 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2444 },
2293 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 2445 },
2294 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2447 },
2295 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 32, .child_index = 2448 },
2296 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2450 },
2297 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 24, .child_index = 2452 },
2298 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2453 },
2299 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2110 },
2300 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2454 },
2301 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2455 },
2302 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2456 },
2303 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2457 },
2304 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2458 },
2305 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2459 },
2306 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2460 },
2307 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2461 },
2308 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2462 },
2309 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2463 },
2310 .{ .char = 'y', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 1528 },
2311 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2464 },
2312 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2465 },
2313 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2466 },
2314 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2467 },
2315 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2468 },
2316 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2469 },
2317 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2470 },
2318 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2472 },
2319 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2473 },
2320 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2474 },
2321 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 13, .child_index = 2476 },
2322 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2479 },
2323 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2481 },
2324 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2482 },
2325 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1379 },
2326 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2483 },
2327 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2484 },
2328 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2485 },
2329 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2487 },
2330 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2488 },
2331 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2491 },
2332 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2492 },
2333 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2495 },
2334 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2496 },
2335 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2497 },
2336 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2498 },
2337 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2499 },
2338 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2501 },
2339 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 2502 },
2340 .{ .char = 'w', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2506 },
2341 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1663 },
2342 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2507 },
2343 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2508 },
2344 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2345 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2509 },
2346 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 2510 },
2347 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2511 },
2348 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2512 },
2349 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2513 },
2350 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2514 },
2351 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2515 },
2352 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 7, .child_index = 2516 },
2353 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2517 },
2354 .{ .char = 'o', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
2355 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2040 },
2356 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2518 },
2357 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 2520 },
2358 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 3, .child_index = 1775 },
2359 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2360 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1733 },
2361 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1577 },
2362 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2521 },
2363 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
2364 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2522 },
2365 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2523 },
2366 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 297 },
2367 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2524 },
2368 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 429 },
2369 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2525 },
2370 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2526 },
2371 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2527 },
2372 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1263, .child_index = 2528 },
2373 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2540 },
2374 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2543 },
2375 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2544 },
2376 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2545 },
2377 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 458 },
2378 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2546 },
2379 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2547 },
2380 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2548 },
2381 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2549 },
2382 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2550 },
2383 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2551 },
2384 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2552 },
2385 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1904 },
2386 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2553 },
2387 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2554 },
2388 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2555 },
2389 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2556 },
2390 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
2391 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2557 },
2392 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2559 },
2393 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2560 },
2394 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2561 },
2395 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2562 },
2396 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 568 },
2397 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 344 },
2398 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2566 },
2399 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 2567 },
2400 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1926 },
2401 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1926 },
2402 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2568 },
2403 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2568 },
2404 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2569 },
2405 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 40, .child_index = 2570 },
2406 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2571 },
2407 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2572 },
2408 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2573 },
2409 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2574 },
2410 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2575 },
2411 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2576 },
2412 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 674 },
2413 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2577 },
2414 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 2578 },
2415 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 584 },
2416 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2579 },
2417 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2580 },
2418 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2581 },
2419 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 2582 },
2420 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2583 },
2421 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2584 },
2422 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 458 },
2423 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 458 },
2424 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 463 },
2425 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
2426 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 519 },
2427 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 412 },
2428 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2585 },
2429 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2586 },
2430 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2587 },
2431 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2588 },
2432 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2259 },
2433 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2589 },
2434 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2590 },
2435 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2259 },
2436 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2591 },
2437 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2592 },
2438 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2589 },
2439 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2591 },
2440 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2589 },
2441 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2260 },
2442 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2593 },
2443 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2594 },
2444 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
2445 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2595 },
2446 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 122, .child_index = 2597 },
2447 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1399 },
2448 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 332 },
2449 .{ .char = 's', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1938 },
2450 .{ .char = 'z', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1938 },
2451 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2614 },
2452 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2615 },
2453 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 332 },
2454 .{ .char = 'c', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 2616 },
2455 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2618 },
2456 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 2619 },
2457 .{ .char = 'c', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 1399 },
2458 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2621 },
2459 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1207 },
2460 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 1708 },
2461 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 463 },
2462 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
2463 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 463 },
2464 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2622 },
2465 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1699 },
2466 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 2623 },
2467 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2625 },
2468 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 463 },
2469 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
2470 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2615 },
2471 .{ .char = 'v', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 549 },
2472 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2288 },
2473 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2626 },
2474 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 14, .child_index = 2628 },
2475 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 2630 },
2476 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2633 },
2477 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2635 },
2478 .{ .char = 'c', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 2616 },
2479 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 332 },
2480 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2618 },
2481 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2636 },
2482 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2638 },
2483 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2639 },
2484 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2640 },
2485 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 2641 },
2486 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2635 },
2487 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2644 },
2488 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2645 },
2489 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2647 },
2490 .{ .char = '2', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2491 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2648 },
2492 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2649 },
2493 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2650 },
2494 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2651 },
2495 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2652 },
2496 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2653 },
2497 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1534 },
2498 .{ .char = '8', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2499 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2654 },
2500 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2655 },
2501 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2656 },
2502 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2657 },
2503 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2658 },
2504 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2659 },
2505 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2660 },
2506 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 25, .child_index = 2661 },
2507 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2662 },
2508 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2663 },
2509 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1795 },
2510 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2664 },
2511 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2665 },
2512 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 729 },
2513 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2666 },
2514 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1494 },
2515 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2667 },
2516 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2669 },
2517 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2670 },
2518 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1197 },
2519 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2671 },
2520 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2672 },
2521 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2673 },
2522 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
2523 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2674 },
2524 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2675 },
2525 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2677 },
2526 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 2678 },
2527 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 15, .child_index = 2679 },
2528 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2680 },
2529 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 479 },
2530 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2681 },
2531 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2682 },
2532 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 2683 },
2533 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 2684 },
2534 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2686 },
2535 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2687 },
2536 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2688 },
2537 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 463 },
2538 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 463 },
2539 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2689 },
2540 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2691 },
2541 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2692 },
2542 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2693 },
2543 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 2694 },
2544 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2695 },
2545 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2696 },
2546 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 2697 },
2547 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2698 },
2548 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2699 },
2549 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2700 },
2550 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 2701 },
2551 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 13, .child_index = 2704 },
2552 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2699 },
2553 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 24, .child_index = 2705 },
2554 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2439 },
2555 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2708 },
2556 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 2709 },
2557 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2711 },
2558 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 2712 },
2559 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2713 },
2560 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2439 },
2561 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2714 },
2562 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 2385 },
2563 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 2715 },
2564 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 2717 },
2565 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2722 },
2566 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2724 },
2567 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 2725 },
2568 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 2725 },
2569 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2727 },
2570 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2728 },
2571 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2729 },
2572 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2730 },
2573 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2731 },
2574 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2732 },
2575 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2733 },
2576 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2736 },
2577 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2737 },
2578 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 2738 },
2579 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2741 },
2580 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2742 },
2581 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2745 },
2582 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2746 },
2583 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2748 },
2584 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2749 },
2585 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2750 },
2586 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2752 },
2587 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2753 },
2588 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2754 },
2589 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2755 },
2590 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2756 },
2591 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2757 },
2592 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2731 },
2593 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2732 },
2594 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2758 },
2595 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2736 },
2596 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2737 },
2597 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2760 },
2598 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 2761 },
2599 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2745 },
2600 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2765 },
2601 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2766 },
2602 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2767 },
2603 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2768 },
2604 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 2769 },
2605 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2773 },
2606 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2775 },
2607 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2779 },
2608 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2609 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2781 },
2610 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 20, .child_index = 2782 },
2611 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 20, .child_index = 2782 },
2612 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2728 },
2613 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2784 },
2614 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2785 },
2615 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2786 },
2616 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2789 },
2617 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2789 },
2618 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2790 },
2619 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2791 },
2620 .{ .char = 'k', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2792 },
2621 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2794 },
2622 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2728 },
2623 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2795 },
2624 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2722 },
2625 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2722 },
2626 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2796 },
2627 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 2797 },
2628 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 2797 },
2629 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2775 },
2630 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2631 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 24, .child_index = 2800 },
2632 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2802 },
2633 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 1567 },
2634 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2803 },
2635 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2804 },
2636 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2805 },
2637 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2806 },
2638 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2807 },
2639 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2808 },
2640 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2809 },
2641 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2810 },
2642 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2811 },
2643 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2812 },
2644 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2813 },
2645 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 412 },
2646 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2814 },
2647 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2815 },
2648 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2819 },
2649 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2820 },
2650 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2822 },
2651 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2824 },
2652 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2825 },
2653 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2826 },
2654 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2827 },
2655 .{ .char = 'e', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 2829 },
2656 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 2830 },
2657 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2835 },
2658 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2836 },
2659 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2837 },
2660 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2838 },
2661 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2839 },
2662 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2840 },
2663 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2841 },
2664 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2840 },
2665 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1379 },
2666 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2842 },
2667 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2843 },
2668 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2844 },
2669 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2845 },
2670 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2842 },
2671 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2846 },
2672 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2843 },
2673 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2844 },
2674 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2847 },
2675 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2848 },
2676 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2850 },
2677 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2851 },
2678 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2852 },
2679 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2853 },
2680 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2855 },
2681 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2856 },
2682 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2857 },
2683 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2858 },
2684 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2856 },
2685 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2859 },
2686 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2687 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2860 },
2688 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2861 },
2689 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 2862 },
2690 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2863 },
2691 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2864 },
2692 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2865 },
2693 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2866 },
2694 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2868 },
2695 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 7, .child_index = 2869 },
2696 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2803 },
2697 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2873 },
2698 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2874 },
2699 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 2875 },
2700 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
2701 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1530 },
2702 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2653 },
2703 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2876 },
2704 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2877 },
2705 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2878 },
2706 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2879 },
2707 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2880 },
2708 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2881 },
2709 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2883 },
2710 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2885 },
2711 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2886 },
2712 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2890 },
2713 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2892 },
2714 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 393, .child_index = 2893 },
2715 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2897 },
2716 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2899 },
2717 .{ .char = 'v', .end_of_word = false, .end_of_list = false, .number = 836, .child_index = 2901 },
2718 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2915 },
2719 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2916 },
2720 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2917 },
2721 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2918 },
2722 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2919 },
2723 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2920 },
2724 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2921 },
2725 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
2726 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2922 },
2727 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2923 },
2728 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2924 },
2729 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2925 },
2730 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2926 },
2731 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2927 },
2732 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2928 },
2733 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1389 },
2734 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
2735 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1671 },
2736 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 506 },
2737 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2929 },
2738 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2930 },
2739 .{ .char = 'z', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2740 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1131 },
2741 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2931 },
2742 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2932 },
2743 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2933 },
2744 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2934 },
2745 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2935 },
2746 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 2936 },
2747 .{ .char = '3', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2311 },
2748 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
2749 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 40, .child_index = 2937 },
2750 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2944 },
2751 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2945 },
2752 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2946 },
2753 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
2754 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2947 },
2755 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2948 },
2756 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2949 },
2757 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 2950 },
2758 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2951 },
2759 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 2952 },
2760 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2953 },
2761 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 2954 },
2762 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1399 },
2763 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 897 },
2764 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2955 },
2765 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2956 },
2766 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2957 },
2767 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2958 },
2768 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2959 },
2769 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2960 },
2770 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2959 },
2771 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2959 },
2772 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2961 },
2773 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2962 },
2774 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2963 },
2775 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2964 },
2776 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 2965 },
2777 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2967 },
2778 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 13, .child_index = 2968 },
2779 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 15, .child_index = 2972 },
2780 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2974 },
2781 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 2976 },
2782 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2980 },
2783 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 2981 },
2784 .{ .char = 'k', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2985 },
2785 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 2986 },
2786 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 2989 },
2787 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2992 },
2788 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 11, .child_index = 2994 },
2789 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 23, .child_index = 2997 },
2790 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3003 },
2791 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3004 },
2792 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 3006 },
2793 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3008 },
2794 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3009 },
2795 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 549 },
2796 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2797 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3010 },
2798 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
2799 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1399 },
2800 .{ .char = 'c', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1399 },
2801 .{ .char = 'b', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 1712 },
2802 .{ .char = '6', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 649 },
2803 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2804 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3011 },
2805 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 463 },
2806 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2635 },
2807 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 3013 },
2808 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3018 },
2809 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3020 },
2810 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3021 },
2811 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3020 },
2812 .{ .char = 't', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 3024 },
2813 .{ .char = 'x', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2814 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3011 },
2815 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3025 },
2816 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3026 },
2817 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3027 },
2818 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3028 },
2819 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
2820 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3029 },
2821 .{ .char = 't', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 3024 },
2822 .{ .char = 'x', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2823 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3031 },
2824 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1800 },
2825 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3032 },
2826 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3033 },
2827 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3034 },
2828 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3035 },
2829 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 512 },
2830 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3036 },
2831 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3037 },
2832 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3038 },
2833 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3039 },
2834 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
2835 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3040 },
2836 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 568 },
2837 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3041 },
2838 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3042 },
2839 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3043 },
2840 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 25, .child_index = 3044 },
2841 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3045 },
2842 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3046 },
2843 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1174 },
2844 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3047 },
2845 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3048 },
2846 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3049 },
2847 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3050 },
2848 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3051 },
2849 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3052 },
2850 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3053 },
2851 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3054 },
2852 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3055 },
2853 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3056 },
2854 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3057 },
2855 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3058 },
2856 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3059 },
2857 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3060 },
2858 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 15, .child_index = 3061 },
2859 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3065 },
2860 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3066 },
2861 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3067 },
2862 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 3068 },
2863 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 3071 },
2864 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3071 },
2865 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3075 },
2866 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2790 },
2867 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 463 },
2868 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3077 },
2869 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3078 },
2870 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3079 },
2871 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3080 },
2872 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3081 },
2873 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 14, .child_index = 3082 },
2874 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3087 },
2875 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3088 },
2876 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 3089 },
2877 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3091 },
2878 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3092 },
2879 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3093 },
2880 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3094 },
2881 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3095 },
2882 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 7, .child_index = 3096 },
2883 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 13, .child_index = 3098 },
2884 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3100 },
2885 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3101 },
2886 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2722 },
2887 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2728 },
2888 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 3102 },
2889 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2728 },
2890 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2722 },
2891 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 3104 },
2892 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2439 },
2893 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2722 },
2894 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2439 },
2895 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2722 },
2896 .{ .char = 'b', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
2897 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
2898 .{ .char = 'h', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
2899 .{ .char = 'v', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
2900 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2901 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2775 },
2902 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
2903 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3106 },
2904 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 3102 },
2905 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2728 },
2906 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2728 },
2907 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3102 },
2908 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3107 },
2909 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2910 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2911 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2912 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3108 },
2913 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2780 },
2914 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2915 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2916 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2917 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2732 },
2918 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2758 },
2919 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3109 },
2920 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2921 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3111 },
2922 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3112 },
2923 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3113 },
2924 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3114 },
2925 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2780 },
2926 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2927 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
2928 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3112 },
2929 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2730 },
2930 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3115 },
2931 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3115 },
2932 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3116 },
2933 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2934 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2935 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3117 },
2936 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2760 },
2937 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2780 },
2938 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
2939 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3117 },
2940 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2780 },
2941 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2732 },
2942 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2758 },
2943 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3109 },
2944 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3118 },
2945 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3120 },
2946 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3107 },
2947 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3107 },
2948 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3121 },
2949 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2779 },
2950 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3122 },
2951 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
2952 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3123 },
2953 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3124 },
2954 .{ .char = 'b', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
2955 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
2956 .{ .char = 'h', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
2957 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2958 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2775 },
2959 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3125 },
2960 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2786 },
2961 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3127 },
2962 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2728 },
2963 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3130 },
2964 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2786 },
2965 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3131 },
2966 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3132 },
2967 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
2968 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
2969 .{ .char = 'v', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2970 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 412 },
2971 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3121 },
2972 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3122 },
2973 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
2974 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3133 },
2975 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3136 },
2976 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2775 },
2977 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2779 },
2978 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2722 },
2979 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 3137 },
2980 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2722 },
2981 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
2982 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3139 },
2983 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3140 },
2984 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3141 },
2985 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3142 },
2986 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3143 },
2987 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2230 },
2988 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3144 },
2989 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3145 },
2990 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3146 },
2991 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 1528 },
2992 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3147 },
2993 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3148 },
2994 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3149 },
2995 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 311 },
2996 .{ .char = 't', .end_of_word = true, .end_of_list = false, .number = 4, .child_index = 3150 },
2997 .{ .char = 'z', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
2998 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 451 },
2999 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 458 },
3000 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 458 },
3001 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3152 },
3002 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3154 },
3003 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3156 },
3004 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3157 },
3005 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3158 },
3006 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3159 },
3007 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2825 },
3008 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3009 .{ .char = 'c', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3010 .{ .char = 'm', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 2829 },
3011 .{ .char = 'n', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 2829 },
3012 .{ .char = 'p', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 2829 },
3013 .{ .char = 'z', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 2829 },
3014 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3160 },
3015 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 2829 },
3016 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3161 },
3017 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3162 },
3018 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3163 },
3019 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 463 },
3020 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3164 },
3021 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3166 },
3022 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
3023 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
3024 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3169 },
3025 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3170 },
3026 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3172 },
3027 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3174 },
3028 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3175 },
3029 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 654 },
3030 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3176 },
3031 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3177 },
3032 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3177 },
3033 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 654 },
3034 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3178 },
3035 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 463 },
3036 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2507 },
3037 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3179 },
3038 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3180 },
3039 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3181 },
3040 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3182 },
3041 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 3183 },
3042 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3184 },
3043 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3185 },
3044 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3186 },
3045 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3187 },
3046 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3188 },
3047 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3189 },
3048 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2243 },
3049 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3190 },
3050 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 585 },
3051 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 664 },
3052 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3193 },
3053 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3194 },
3054 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 1534 },
3055 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 450 },
3056 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3195 },
3057 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3196 },
3058 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3197 },
3059 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3198 },
3060 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3199 },
3061 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3200 },
3062 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3201 },
3063 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3202 },
3064 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3203 },
3065 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3204 },
3066 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3205 },
3067 .{ .char = 'v', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 3206 },
3068 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3208 },
3069 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3209 },
3070 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3198 },
3071 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3210 },
3072 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3211 },
3073 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3208 },
3074 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3212 },
3075 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 388, .child_index = 3213 },
3076 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3204 },
3077 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3225 },
3078 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3208 },
3079 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3227 },
3080 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 36, .child_index = 3228 },
3081 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 15, .child_index = 3230 },
3082 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 71, .child_index = 3231 },
3083 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 45, .child_index = 3234 },
3084 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 3235 },
3085 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 294, .child_index = 3237 },
3086 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 32, .child_index = 3244 },
3087 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 35, .child_index = 3245 },
3088 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 81, .child_index = 3246 },
3089 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3251 },
3090 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3252 },
3091 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 42, .child_index = 3253 },
3092 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 163, .child_index = 3259 },
3093 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3267 },
3094 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2892 },
3095 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3268 },
3096 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3269 },
3097 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3268 },
3098 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3270 },
3099 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3271 },
3100 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3272 },
3101 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3273 },
3102 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3274 },
3103 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3275 },
3104 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3276 },
3105 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3277 },
3106 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3278 },
3107 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
3108 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3279 },
3109 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3280 },
3110 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3281 },
3111 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3282 },
3112 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3283 },
3113 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3284 },
3114 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3285 },
3115 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 3286 },
3116 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3287 },
3117 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2245 },
3118 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3289 },
3119 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3290 },
3120 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3291 },
3121 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3292 },
3122 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3293 },
3123 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3294 },
3124 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3295 },
3125 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3296 },
3126 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3297 },
3127 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3298 },
3128 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3299 },
3129 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 3300 },
3130 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3301 },
3131 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3302 },
3132 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3303 },
3133 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 3304 },
3134 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3305 },
3135 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 486 },
3136 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3306 },
3137 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3307 },
3138 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3308 },
3139 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2959 },
3140 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3309 },
3141 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
3142 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3310 },
3143 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3311 },
3144 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3312 },
3145 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3313 },
3146 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3314 },
3147 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3315 },
3148 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3316 },
3149 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3317 },
3150 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3318 },
3151 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 3319 },
3152 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3321 },
3153 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3322 },
3154 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3323 },
3155 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3324 },
3156 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1948 },
3157 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3325 },
3158 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3326 },
3159 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3328 },
3160 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3330 },
3161 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2865 },
3162 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 3331 },
3163 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3332 },
3164 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3333 },
3165 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3334 },
3166 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3335 },
3167 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3336 },
3168 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3337 },
3169 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3338 },
3170 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3339 },
3171 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3340 },
3172 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3341 },
3173 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3342 },
3174 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 3343 },
3175 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3344 },
3176 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3345 },
3177 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3351 },
3178 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3352 },
3179 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3353 },
3180 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3354 },
3181 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3356 },
3182 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3357 },
3183 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3352 },
3184 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3358 },
3185 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3359 },
3186 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 3360 },
3187 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3361 },
3188 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3362 },
3189 .{ .char = 'x', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3181 },
3190 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 648 },
3191 .{ .char = '8', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3192 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3363 },
3193 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 3365 },
3194 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3020 },
3195 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3363 },
3196 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3363 },
3197 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 3365 },
3198 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3020 },
3199 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3365 },
3200 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3363 },
3201 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3363 },
3202 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3363 },
3203 .{ .char = '1', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 648 },
3204 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3026 },
3205 .{ .char = '1', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 648 },
3206 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3366 },
3207 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 238 },
3208 .{ .char = '8', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3209 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2319 },
3210 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3367 },
3211 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3368 },
3212 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3369 },
3213 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3370 },
3214 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3371 },
3215 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3372 },
3216 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
3217 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3373 },
3218 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3374 },
3219 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 581 },
3220 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3375 },
3221 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3376 },
3222 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3377 },
3223 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 25, .child_index = 3378 },
3224 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3379 },
3225 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3380 },
3226 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 450 },
3227 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3381 },
3228 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 569 },
3229 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3382 },
3230 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3383 },
3231 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 458 },
3232 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3384 },
3233 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2343 },
3234 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3385 },
3235 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3052 },
3236 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3386 },
3237 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3387 },
3238 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3388 },
3239 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3389 },
3240 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 3390 },
3241 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 569 },
3242 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3392 },
3243 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 569 },
3244 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 519 },
3245 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3394 },
3246 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3395 },
3247 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3396 },
3248 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3398 },
3249 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3400 },
3250 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3401 },
3251 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3402 },
3252 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3404 },
3253 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3405 },
3254 .{ .char = 'p', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 3406 },
3255 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3407 },
3256 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3408 },
3257 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3409 },
3258 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2248 },
3259 .{ .char = 'b', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3408 },
3260 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3410 },
3261 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3411 },
3262 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3413 },
3263 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3415 },
3264 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3416 },
3265 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3408 },
3266 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3417 },
3267 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3418 },
3268 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 17, .child_index = 3419 },
3269 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3065 },
3270 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3421 },
3271 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
3272 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3418 },
3273 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 451 },
3274 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3422 },
3275 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 3423 },
3276 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3418 },
3277 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 7, .child_index = 3390 },
3278 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3392 },
3279 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
3280 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 3127 },
3281 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2779 },
3282 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
3283 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 2722 },
3284 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2722 },
3285 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 568 },
3286 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3424 },
3287 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3426 },
3288 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3125 },
3289 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
3290 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2765 },
3291 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
3292 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2746 },
3293 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3427 },
3294 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3428 },
3295 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
3296 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
3297 .{ .char = 'h', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3298 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3299 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3431 },
3300 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
3301 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
3302 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2794 },
3303 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
3304 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3305 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3306 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2779 },
3307 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 2779 },
3308 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
3309 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2790 },
3310 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2765 },
3311 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3131 },
3312 .{ .char = 'b', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3313 .{ .char = 'h', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3314 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3315 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 2722 },
3316 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 3102 },
3317 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3432 },
3318 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 1766 },
3319 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2053 },
3320 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3434 },
3321 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3435 },
3322 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3436 },
3323 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3437 },
3324 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3439 },
3325 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3440 },
3326 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 463 },
3327 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3441 },
3328 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3442 },
3329 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3443 },
3330 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3331 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 3444 },
3332 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3444 },
3333 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2560 },
3334 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2560 },
3335 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3445 },
3336 .{ .char = 'b', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 2829 },
3337 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 2829 },
3338 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3446 },
3339 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3447 },
3340 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 2829 },
3341 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3448 },
3342 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3449 },
3343 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 585 },
3344 .{ .char = '4', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
3345 .{ .char = 'e', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3346 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3347 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3348 .{ .char = 'u', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3349 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3450 },
3350 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3452 },
3351 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 3408 },
3352 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3408 },
3353 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3453 },
3354 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3454 },
3355 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3455 },
3356 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1389 },
3357 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3456 },
3358 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3164 },
3359 .{ .char = 'v', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 3458 },
3360 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3361 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3460 },
3362 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 3461 },
3363 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3462 },
3364 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3463 },
3365 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3464 },
3366 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3465 },
3367 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3466 },
3368 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3467 },
3369 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 463 },
3370 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 457 },
3371 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
3372 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3468 },
3373 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3469 },
3374 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2878 },
3375 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3470 },
3376 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 238 },
3377 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3210 },
3378 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3210 },
3379 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3471 },
3380 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3472 },
3381 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3473 },
3382 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3474 },
3383 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3475 },
3384 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3476 },
3385 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3477 },
3386 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3478 },
3387 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3481 },
3388 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3482 },
3389 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3483 },
3390 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3484 },
3391 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3485 },
3392 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 18, .child_index = 3486 },
3393 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3488 },
3394 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 20, .child_index = 3489 },
3395 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3491 },
3396 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 242, .child_index = 3492 },
3397 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 3497 },
3398 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3498 },
3399 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3500 },
3400 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 3501 },
3401 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3502 },
3402 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 42, .child_index = 3504 },
3403 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3508 },
3404 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3509 },
3405 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 412 },
3406 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3510 },
3407 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 30, .child_index = 3511 },
3408 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3512 },
3409 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 15, .child_index = 3513 },
3410 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 30, .child_index = 3515 },
3411 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3516 },
3412 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 40, .child_index = 3517 },
3413 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 45, .child_index = 3518 },
3414 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3519 },
3415 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3516 },
3416 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3520 },
3417 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3521 },
3418 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3522 },
3419 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 186, .child_index = 3523 },
3420 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 36, .child_index = 3528 },
3421 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 3529 },
3422 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 20, .child_index = 3530 },
3423 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 32, .child_index = 3532 },
3424 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 35, .child_index = 3536 },
3425 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 18, .child_index = 3542 },
3426 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 18, .child_index = 3543 },
3427 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 3544 },
3428 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 34, .child_index = 3545 },
3429 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3546 },
3430 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3547 },
3431 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3548 },
3432 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3549 },
3433 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3550 },
3434 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 3551 },
3435 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3553 },
3436 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 3554 },
3437 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3555 },
3438 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 3556 },
3439 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3561 },
3440 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3562 },
3441 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3563 },
3442 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 3564 },
3443 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 24, .child_index = 3564 },
3444 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 48, .child_index = 3566 },
3445 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 36, .child_index = 3572 },
3446 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3251 },
3447 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3574 },
3448 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3575 },
3449 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3576 },
3450 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3577 },
3451 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3578 },
3452 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3579 },
3453 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3369 },
3454 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3583 },
3455 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3584 },
3456 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3585 },
3457 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3586 },
3458 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
3459 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1665 },
3460 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2640 },
3461 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3588 },
3462 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2343 },
3463 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3056 },
3464 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3589 },
3465 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 3590 },
3466 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3591 },
3467 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3591 },
3468 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3592 },
3469 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 1171 },
3470 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3593 },
3471 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2245 },
3472 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3290 },
3473 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 1171 },
3474 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3594 },
3475 .{ .char = 'h', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 1171 },
3476 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3595 },
3477 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3596 },
3478 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3597 },
3479 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 3598 },
3480 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
3481 .{ .char = 'E', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3599 },
3482 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3600 },
3483 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 10, .child_index = 3601 },
3484 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
3485 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3606 },
3486 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3607 },
3487 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3608 },
3488 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3609 },
3489 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3610 },
3490 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3611 },
3491 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3612 },
3492 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3613 },
3493 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3614 },
3494 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3615 },
3495 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
3496 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3616 },
3497 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3617 },
3498 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3618 },
3499 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3619 },
3500 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3620 },
3501 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3626 },
3502 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2555 },
3503 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3342 },
3504 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3627 },
3505 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3628 },
3506 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3629 },
3507 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3630 },
3508 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3631 },
3509 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3632 },
3510 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 3633 },
3511 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3634 },
3512 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3636 },
3513 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3637 },
3514 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
3515 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3638 },
3516 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3640 },
3517 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3641 },
3518 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3642 },
3519 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3643 },
3520 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3644 },
3521 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 680 },
3522 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 3645 },
3523 .{ .char = 'q', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 3646 },
3524 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3648 },
3525 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3649 },
3526 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3651 },
3527 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3652 },
3528 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 3653 },
3529 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3655 },
3530 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3656 },
3531 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
3532 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3657 },
3533 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3658 },
3534 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
3535 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3659 },
3536 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3660 },
3537 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3658 },
3538 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3661 },
3539 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 3662 },
3540 .{ .char = 'T', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3663 },
3541 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3664 },
3542 .{ .char = 'b', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3543 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3544 .{ .char = 'x', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3545 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
3546 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3456 },
3547 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3665 },
3548 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3579 },
3549 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3666 },
3550 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3667 },
3551 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3668 },
3552 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3669 },
3553 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3670 },
3554 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3671 },
3555 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3672 },
3556 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3673 },
3557 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 25, .child_index = 3674 },
3558 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3675 },
3559 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3676 },
3560 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3677 },
3561 .{ .char = 'c', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3442 },
3562 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3678 },
3563 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2672 },
3564 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3679 },
3565 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3680 },
3566 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3681 },
3567 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3682 },
3568 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3683 },
3569 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3684 },
3570 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3686 },
3571 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3687 },
3572 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3690 },
3573 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2790 },
3574 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3691 },
3575 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3692 },
3576 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3693 },
3577 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3695 },
3578 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3400 },
3579 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3696 },
3580 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3698 },
3581 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3699 },
3582 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3700 },
3583 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3701 },
3584 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3401 },
3585 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
3586 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3702 },
3587 .{ .char = 'u', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3588 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3705 },
3589 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
3590 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 656 },
3591 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3698 },
3592 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3707 },
3593 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3708 },
3594 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3709 },
3595 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3711 },
3596 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3713 },
3597 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3714 },
3598 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 3716 },
3599 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 7, .child_index = 3718 },
3600 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3720 },
3601 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3721 },
3602 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 3724 },
3603 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3727 },
3604 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3727 },
3605 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
3606 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3728 },
3607 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2780 },
3608 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3609 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3610 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3427 },
3611 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3730 },
3612 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3731 },
3613 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3732 },
3614 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3733 },
3615 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3734 },
3616 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3735 },
3617 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3736 },
3618 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3737 },
3619 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3738 },
3620 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3739 },
3621 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3622 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3740 },
3623 .{ .char = 'z', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3624 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3741 },
3625 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 2829 },
3626 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3742 },
3627 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3743 },
3628 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3744 },
3629 .{ .char = '0', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3630 .{ .char = '1', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3631 .{ .char = 'i', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3632 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 412 },
3633 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3745 },
3634 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3747 },
3635 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3636 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3637 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3748 },
3638 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3749 },
3639 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3750 },
3640 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 3751 },
3641 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3752 },
3642 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3753 },
3643 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3754 },
3644 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3755 },
3645 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3756 },
3646 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3757 },
3647 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3579 },
3648 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3468 },
3649 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
3650 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3758 },
3651 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3759 },
3652 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3204 },
3653 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3760 },
3654 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3761 },
3655 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3762 },
3656 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3763 },
3657 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3765 },
3658 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3765 },
3659 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3765 },
3660 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3766 },
3661 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3767 },
3662 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3768 },
3663 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3770 },
3664 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3771 },
3665 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3772 },
3666 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3773 },
3667 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 3774 },
3668 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3776 },
3669 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3777 },
3670 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3778 },
3671 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3779 },
3672 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3780 },
3673 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 206, .child_index = 3781 },
3674 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 18, .child_index = 3786 },
3675 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3787 },
3676 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 3788 },
3677 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3789 },
3678 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3790 },
3679 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3791 },
3680 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 3792 },
3681 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3793 },
3682 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3794 },
3683 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3795 },
3684 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3796 },
3685 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3796 },
3686 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 3798 },
3687 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3500 },
3688 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3799 },
3689 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3800 },
3690 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 30, .child_index = 3801 },
3691 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3547 },
3692 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3803 },
3693 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3807 },
3694 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 30, .child_index = 3801 },
3695 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3808 },
3696 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 40, .child_index = 3809 },
3697 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 45, .child_index = 3813 },
3698 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3547 },
3699 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 3815 },
3700 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 3816 },
3701 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 3817 },
3702 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 30, .child_index = 3818 },
3703 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3820 },
3704 .{ .char = 'k', .end_of_word = false, .end_of_list = false, .number = 114, .child_index = 3821 },
3705 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 18, .child_index = 3825 },
3706 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 3826 },
3707 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 36, .child_index = 3827 },
3708 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 3829 },
3709 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3831 },
3710 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 3832 },
3711 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3834 },
3712 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 3835 },
3713 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3837 },
3714 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3838 },
3715 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3840 },
3716 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3841 },
3717 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 3842 },
3718 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3845 },
3719 .{ .char = 'u', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 3846 },
3720 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3807 },
3721 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 3849 },
3722 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 3849 },
3723 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3850 },
3724 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 34, .child_index = 3852 },
3725 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3854 },
3726 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3855 },
3727 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3856 },
3728 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3857 },
3729 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3858 },
3730 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 3860 },
3731 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 3861 },
3732 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3862 },
3733 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3863 },
3734 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3553 },
3735 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3864 },
3736 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 3865 },
3737 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3868 },
3738 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3869 },
3739 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3865 },
3740 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3870 },
3741 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3871 },
3742 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3872 },
3743 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 18, .child_index = 3873 },
3744 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3875 },
3745 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 3876 },
3746 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3877 },
3747 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 16, .child_index = 3878 },
3748 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3882 },
3749 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3883 },
3750 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 16, .child_index = 3878 },
3751 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 30, .child_index = 3801 },
3752 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3884 },
3753 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3886 },
3754 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3888 },
3755 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3889 },
3756 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3890 },
3757 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
3758 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 648 },
3759 .{ .char = '3', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2311 },
3760 .{ .char = '6', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 649 },
3761 .{ .char = '8', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3762 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3891 },
3763 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3894 },
3764 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3895 },
3765 .{ .char = 'i', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3766 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 549 },
3767 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2343 },
3768 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3898 },
3769 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 3899 },
3770 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 1171 },
3771 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3591 },
3772 .{ .char = 'b', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 1171 },
3773 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3900 },
3774 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3901 },
3775 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 323 },
3776 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 1699 },
3777 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 3902 },
3778 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3903 },
3779 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 3024 },
3780 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 648 },
3781 .{ .char = '8', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3782 .{ .char = 'A', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3904 },
3783 .{ .char = 'P', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3046 },
3784 .{ .char = 'S', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3905 },
3785 .{ .char = 'M', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3906 },
3786 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3907 },
3787 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 521 },
3788 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2507 },
3789 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3908 },
3790 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3909 },
3791 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3910 },
3792 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3911 },
3793 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3912 },
3794 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3913 },
3795 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3914 },
3796 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3918 },
3797 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3919 },
3798 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3920 },
3799 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3922 },
3800 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3923 },
3801 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3924 },
3802 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 3925 },
3803 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3927 },
3804 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3928 },
3805 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3929 },
3806 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3930 },
3807 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3659 },
3808 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3931 },
3809 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3932 },
3810 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3933 },
3811 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3934 },
3812 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 3935 },
3813 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3936 },
3814 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2934 },
3815 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3937 },
3816 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3342 },
3817 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3938 },
3818 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3819 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3939 },
3820 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3940 },
3821 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3941 },
3822 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3942 },
3823 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3943 },
3824 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 3944 },
3825 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3947 },
3826 .{ .char = 'f', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3827 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3948 },
3828 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3949 },
3829 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3950 },
3830 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3951 },
3831 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3950 },
3832 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3952 },
3833 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3954 },
3834 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3955 },
3835 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3956 },
3836 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3958 },
3837 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3959 },
3838 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 680 },
3839 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3960 },
3840 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3961 },
3841 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 3962 },
3842 .{ .char = 'T', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 3964 },
3843 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3966 },
3844 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3967 },
3845 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3968 },
3846 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3969 },
3847 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3970 },
3848 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 664 },
3849 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 344 },
3850 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3971 },
3851 .{ .char = 'j', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3972 },
3852 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3973 },
3853 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 25, .child_index = 3974 },
3854 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3975 },
3855 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3679 },
3856 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3976 },
3857 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3977 },
3858 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 579 },
3859 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3978 },
3860 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2237 },
3861 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3979 },
3862 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3980 },
3863 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 656 },
3864 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3981 },
3865 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3982 },
3866 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 656 },
3867 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 412 },
3868 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3418 },
3869 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3985 },
3870 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2568 },
3871 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3698 },
3872 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3698 },
3873 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3698 },
3874 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3400 },
3875 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3987 },
3876 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3988 },
3877 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 578 },
3878 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3990 },
3879 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3992 },
3880 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3993 },
3881 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3994 },
3882 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3996 },
3883 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3884 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3997 },
3885 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3998 },
3886 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3999 },
3887 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4000 },
3888 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4001 },
3889 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3981 },
3890 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3401 },
3891 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4002 },
3892 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3698 },
3893 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 656 },
3894 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 412 },
3895 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 4003 },
3896 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4005 },
3897 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4006 },
3898 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4008 },
3899 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4010 },
3900 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 656 },
3901 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 412 },
3902 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3981 },
3903 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 656 },
3904 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 412 },
3905 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3980 },
3906 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4011 },
3907 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2780 },
3908 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2780 },
3909 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4014 },
3910 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4015 },
3911 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4016 },
3912 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4017 },
3913 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4018 },
3914 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4019 },
3915 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2507 },
3916 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4020 },
3917 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4021 },
3918 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4022 },
3919 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3920 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4023 },
3921 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 2829 },
3922 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4024 },
3923 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4025 },
3924 .{ .char = '4', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
3925 .{ .char = '8', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
3926 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4026 },
3927 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4027 },
3928 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3748 },
3929 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4028 },
3930 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4029 },
3931 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4030 },
3932 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4031 },
3933 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4032 },
3934 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4033 },
3935 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4035 },
3936 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4036 },
3937 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4037 },
3938 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4038 },
3939 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4041 },
3940 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1197 },
3941 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4042 },
3942 .{ .char = 'M', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4043 },
3943 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4044 },
3944 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4045 },
3945 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4046 },
3946 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4047 },
3947 .{ .char = 'M', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4049 },
3948 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4050 },
3949 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4051 },
3950 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4052 },
3951 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4054 },
3952 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3791 },
3953 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4056 },
3954 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4057 },
3955 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4054 },
3956 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4060 },
3957 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3791 },
3958 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3773 },
3959 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4062 },
3960 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 15, .child_index = 4063 },
3961 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 4065 },
3962 .{ .char = 'k', .end_of_word = false, .end_of_list = false, .number = 170, .child_index = 4066 },
3963 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 4069 },
3964 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4070 },
3965 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 4071 },
3966 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4073 },
3967 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4057 },
3968 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4074 },
3969 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4074 },
3970 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4075 },
3971 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4076 },
3972 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4077 },
3973 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4078 },
3974 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4079 },
3975 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 4082 },
3976 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4082 },
3977 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4054 },
3978 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4083 },
3979 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4085 },
3980 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 18, .child_index = 4086 },
3981 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4088 },
3982 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4090 },
3983 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4090 },
3984 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4090 },
3985 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4090 },
3986 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4091 },
3987 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4092 },
3988 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 4093 },
3989 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 4096 },
3990 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4097 },
3991 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 24, .child_index = 4099 },
3992 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 27, .child_index = 4101 },
3993 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 4103 },
3994 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4105 },
3995 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4105 },
3996 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4105 },
3997 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 18, .child_index = 4107 },
3998 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4105 },
3999 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4105 },
4000 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 28, .child_index = 4109 },
4001 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 30, .child_index = 4113 },
4002 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 28, .child_index = 4109 },
4003 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 28, .child_index = 4109 },
4004 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 4107 },
4005 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4105 },
4006 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 18, .child_index = 4118 },
4007 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 3825 },
4008 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 4119 },
4009 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4120 },
4010 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4121 },
4011 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 4105 },
4012 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4122 },
4013 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4124 },
4014 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 4125 },
4015 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4125 },
4016 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4126 },
4017 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3834 },
4018 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3837 },
4019 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4127 },
4020 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4129 },
4021 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 4130 },
4022 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4131 },
4023 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4131 },
4024 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4132 },
4025 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3840 },
4026 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3841 },
4027 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3845 },
4028 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 4086 },
4029 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4133 },
4030 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4134 },
4031 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 22, .child_index = 4135 },
4032 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4088 },
4033 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4137 },
4034 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4138 },
4035 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3807 },
4036 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3862 },
4037 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4077 },
4038 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4077 },
4039 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4140 },
4040 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4140 },
4041 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4141 },
4042 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4142 },
4043 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3877 },
4044 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3864 },
4045 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3868 },
4046 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3869 },
4047 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4143 },
4048 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4145 },
4049 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4146 },
4050 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4147 },
4051 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4148 },
4052 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3875 },
4053 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4149 },
4054 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4151 },
4055 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4152 },
4056 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4155 },
4057 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 3876 },
4058 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3877 },
4059 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3882 },
4060 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3883 },
4061 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4156 },
4062 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4158 },
4063 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3862 },
4064 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4159 },
4065 .{ .char = '3', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2311 },
4066 .{ .char = '6', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 649 },
4067 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4161 },
4068 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4162 },
4069 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4164 },
4070 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4071 .{ .char = 'i', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4072 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 549 },
4073 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1389 },
4074 .{ .char = 'i', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4075 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 549 },
4076 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3586 },
4077 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3367 },
4078 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 33, .child_index = 4165 },
4079 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4173 },
4080 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4174 },
4081 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 4175 },
4082 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4176 },
4083 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 1708 },
4084 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 2622 },
4085 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4177 },
4086 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4178 },
4087 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4179 },
4088 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4180 },
4089 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4181 },
4090 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4182 },
4091 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4183 },
4092 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 680 },
4093 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 458 },
4094 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 568 },
4095 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 569 },
4096 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 569 },
4097 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4184 },
4098 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4185 },
4099 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4186 },
4100 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4188 },
4101 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2680 },
4102 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3927 },
4103 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4189 },
4104 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4190 },
4105 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4191 },
4106 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4193 },
4107 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4194 },
4108 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 654 },
4109 .{ .char = '3', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
4110 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4195 },
4111 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4196 },
4112 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4197 },
4113 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4198 },
4114 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4199 },
4115 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4200 },
4116 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4201 },
4117 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4202 },
4118 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4203 },
4119 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4204 },
4120 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4205 },
4121 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4206 },
4122 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4207 },
4123 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4208 },
4124 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4209 },
4125 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4210 },
4126 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4211 },
4127 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4212 },
4128 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4213 },
4129 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4214 },
4130 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4215 },
4131 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4217 },
4132 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4218 },
4133 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4220 },
4134 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4221 },
4135 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4222 },
4136 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3011 },
4137 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4223 },
4138 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 549 },
4139 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4224 },
4140 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4225 },
4141 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 4226 },
4142 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4227 },
4143 .{ .char = 'A', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 4228 },
4144 .{ .char = 'T', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4145 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
4146 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4229 },
4147 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4230 },
4148 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 4, .child_index = 4231 },
4149 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
4150 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4233 },
4151 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1840 },
4152 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4234 },
4153 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 25, .child_index = 4235 },
4154 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4247 },
4155 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4248 },
4156 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4249 },
4157 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4250 },
4158 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
4159 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4251 },
4160 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4254 },
4161 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 656 },
4162 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3981 },
4163 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4164 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 412 },
4165 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4256 },
4166 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4256 },
4167 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4256 },
4168 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4256 },
4169 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3401 },
4170 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4257 },
4171 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4258 },
4172 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4260 },
4173 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2507 },
4174 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4261 },
4175 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 656 },
4176 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4262 },
4177 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3997 },
4178 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3998 },
4179 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4263 },
4180 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3981 },
4181 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4264 },
4182 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3997 },
4183 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4005 },
4184 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4265 },
4185 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4266 },
4186 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4267 },
4187 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4268 },
4188 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4271 },
4189 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4256 },
4190 .{ .char = 'd', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4191 .{ .char = 'h', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4192 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4193 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
4194 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 2779 },
4195 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4272 },
4196 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4273 },
4197 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4275 },
4198 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4276 },
4199 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4277 },
4200 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3196 },
4201 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4278 },
4202 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4279 },
4203 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4280 },
4204 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4281 },
4205 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3456 },
4206 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3308 },
4207 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4284 },
4208 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4285 },
4209 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4286 },
4210 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4287 },
4211 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4288 },
4212 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4289 },
4213 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4290 },
4214 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4291 },
4215 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3676 },
4216 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4041 },
4217 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4292 },
4218 .{ .char = 'i', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4219 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4292 },
4220 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4293 },
4221 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1197 },
4222 .{ .char = 'M', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1197 },
4223 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1197 },
4224 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4294 },
4225 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4295 },
4226 .{ .char = 'M', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4296 },
4227 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 654 },
4228 .{ .char = 'M', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4296 },
4229 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 654 },
4230 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4297 },
4231 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4298 },
4232 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4299 },
4233 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3791 },
4234 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3791 },
4235 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4300 },
4236 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4301 },
4237 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4302 },
4238 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4303 },
4239 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4304 },
4240 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4305 },
4241 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3791 },
4242 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 4306 },
4243 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3791 },
4244 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3791 },
4245 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4307 },
4246 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 84, .child_index = 4309 },
4247 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 84, .child_index = 4309 },
4248 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4306 },
4249 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3791 },
4250 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 4314 },
4251 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4069 },
4252 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3791 },
4253 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3791 },
4254 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4315 },
4255 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4057 },
4256 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4317 },
4257 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4318 },
4258 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4146 },
4259 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4319 },
4260 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4320 },
4261 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4321 },
4262 .{ .char = 'M', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 344 },
4263 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 344 },
4264 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3761 },
4265 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3547 },
4266 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4322 },
4267 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3547 },
4268 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3547 },
4269 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4324 },
4270 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4325 },
4271 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4326 },
4272 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4077 },
4273 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4077 },
4274 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4077 },
4275 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4327 },
4276 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4077 },
4277 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4077 },
4278 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 12, .child_index = 4329 },
4279 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4329 },
4280 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 4331 },
4281 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 4332 },
4282 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 4331 },
4283 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4331 },
4284 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3547 },
4285 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3547 },
4286 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 4334 },
4287 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4334 },
4288 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4335 },
4289 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 4336 },
4290 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 4336 },
4291 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4338 },
4292 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4341 },
4293 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4335 },
4294 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 4336 },
4295 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 4336 },
4296 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4338 },
4297 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 18, .child_index = 4107 },
4298 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4343 },
4299 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4343 },
4300 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3858 },
4301 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3862 },
4302 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3862 },
4303 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4345 },
4304 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 3838 },
4305 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 3834 },
4306 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3841 },
4307 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3845 },
4308 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4346 },
4309 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4347 },
4310 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4127 },
4311 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3841 },
4312 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4349 },
4313 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4351 },
4314 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 4352 },
4315 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4322 },
4316 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4325 },
4317 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4325 },
4318 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4325 },
4319 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 12, .child_index = 4354 },
4320 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4356 },
4321 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4357 },
4322 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3864 },
4323 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3869 },
4324 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3864 },
4325 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4359 },
4326 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4361 },
4327 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4362 },
4328 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 4363 },
4329 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4363 },
4330 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4364 },
4331 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3877 },
4332 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 3882 },
4333 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3883 },
4334 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4365 },
4335 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3877 },
4336 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3883 },
4337 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3877 },
4338 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4366 },
4339 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4366 },
4340 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4367 },
4341 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4369 },
4342 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4369 },
4343 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4370 },
4344 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 4371 },
4345 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4373 },
4346 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 4374 },
4347 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 10, .child_index = 4375 },
4348 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4379 },
4349 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4380 },
4350 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4381 },
4351 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4382 },
4352 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4383 },
4353 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4384 },
4354 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 10, .child_index = 4385 },
4355 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4387 },
4356 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4388 },
4357 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4389 },
4358 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4390 },
4359 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4391 },
4360 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4392 },
4361 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4394 },
4362 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4395 },
4363 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4396 },
4364 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4399 },
4365 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4400 },
4366 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4401 },
4367 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4402 },
4368 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 405 },
4369 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4403 },
4370 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4404 },
4371 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 459 },
4372 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4405 },
4373 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4406 },
4374 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4407 },
4375 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4409 },
4376 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4410 },
4377 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4411 },
4378 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4412 },
4379 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4413 },
4380 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4414 },
4381 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4415 },
4382 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4416 },
4383 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4418 },
4384 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2319 },
4385 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4420 },
4386 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4421 },
4387 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4422 },
4388 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4423 },
4389 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3979 },
4390 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4424 },
4391 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4425 },
4392 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4426 },
4393 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4427 },
4394 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 569 },
4395 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4428 },
4396 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4429 },
4397 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4430 },
4398 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4428 },
4399 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
4400 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4431 },
4401 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3941 },
4402 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4432 },
4403 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4434 },
4404 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3648 },
4405 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4435 },
4406 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4436 },
4407 .{ .char = 'T', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4408 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4437 },
4409 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4438 },
4410 .{ .char = 'f', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 3024 },
4411 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4412 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4439 },
4413 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4440 },
4414 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4441 },
4415 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4443 },
4416 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4444 },
4417 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4447 },
4418 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4448 },
4419 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4450 },
4420 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 2245 },
4421 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4451 },
4422 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3609 },
4423 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4452 },
4424 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4454 },
4425 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4457 },
4426 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4458 },
4427 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4459 },
4428 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4460 },
4429 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4461 },
4430 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 656 },
4431 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 412 },
4432 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4433 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 656 },
4434 .{ .char = 'w', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4435 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4462 },
4436 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4463 },
4437 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3401 },
4438 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3405 },
4439 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4464 },
4440 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2507 },
4441 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4465 },
4442 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4466 },
4443 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3405 },
4444 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4467 },
4445 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3698 },
4446 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4468 },
4447 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4469 },
4448 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4266 },
4449 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4470 },
4450 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4471 },
4451 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4472 },
4452 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1893 },
4453 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4473 },
4454 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4474 },
4455 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 460 },
4456 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 4475 },
4457 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4476 },
4458 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4477 },
4459 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4478 },
4460 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 2137 },
4461 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4479 },
4462 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1379 },
4463 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4480 },
4464 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4481 },
4465 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4482 },
4466 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4483 },
4467 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4484 },
4468 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4485 },
4469 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4486 },
4470 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4487 },
4471 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 344 },
4472 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4488 },
4473 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 344 },
4474 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
4475 .{ .char = 'M', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4476 .{ .char = '3', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4489 },
4477 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4490 },
4478 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4491 },
4479 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4492 },
4480 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4493 },
4481 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3807 },
4482 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3807 },
4483 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4077 },
4484 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4494 },
4485 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4496 },
4486 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4497 },
4487 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4497 },
4488 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4498 },
4489 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 4499 },
4490 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 36, .child_index = 4501 },
4491 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 8, .child_index = 4504 },
4492 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 28, .child_index = 4507 },
4493 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4306 },
4494 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4493 },
4495 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4493 },
4496 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4146 },
4497 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4508 },
4498 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3870 },
4499 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3870 },
4500 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4510 },
4501 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 4511 },
4502 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4511 },
4503 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4512 },
4504 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4513 },
4505 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4516 },
4506 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4091 },
4507 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4517 },
4508 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 4518 },
4509 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4518 },
4510 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4519 },
4511 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 9, .child_index = 4520 },
4512 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4520 },
4513 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4521 },
4514 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4522 },
4515 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4522 },
4516 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4522 },
4517 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4524 },
4518 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4522 },
4519 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4525 },
4520 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4526 },
4521 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4526 },
4522 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4527 },
4523 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4527 },
4524 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4529 },
4525 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4359 },
4526 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4131 },
4527 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4131 },
4528 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4530 },
4529 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4530 },
4530 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4531 },
4531 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 6, .child_index = 3855 },
4532 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4533 },
4533 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4527 },
4534 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4534 },
4535 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4536 },
4536 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4508 },
4537 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4508 },
4538 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4539 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
4540 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4538 },
4541 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4539 },
4542 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3875 },
4543 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4540 },
4544 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4536 },
4545 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3862 },
4546 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4542 },
4547 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2230 },
4548 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4543 },
4549 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4544 },
4550 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4545 },
4551 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4546 },
4552 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4547 },
4553 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4548 },
4554 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4549 },
4555 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4380 },
4556 .{ .char = 't', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4381 },
4557 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4382 },
4558 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4550 },
4559 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4554 },
4560 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4555 },
4561 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4556 },
4562 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4557 },
4563 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4558 },
4564 .{ .char = 'r', .end_of_word = false, .end_of_list = false, .number = 5, .child_index = 4559 },
4565 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4560 },
4566 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4561 },
4567 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4562 },
4568 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4563 },
4569 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4564 },
4570 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4565 },
4571 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 311 },
4572 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 460 },
4573 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4566 },
4574 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4568 },
4575 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4569 },
4576 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4571 },
4577 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2214 },
4578 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4572 },
4579 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4573 },
4580 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3913 },
4581 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4574 },
4582 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
4583 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
4584 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4575 },
4585 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4576 },
4586 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 3637 },
4587 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4577 },
4588 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4578 },
4589 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4579 },
4590 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
4591 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4580 },
4592 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4582 },
4593 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4583 },
4594 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4584 },
4595 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 1389 },
4596 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 451 },
4597 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4420 },
4598 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4585 },
4599 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4586 },
4600 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4587 },
4601 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4588 },
4602 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4589 },
4603 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3324 },
4604 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 579 },
4605 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4590 },
4606 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4591 },
4607 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1940 },
4608 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4592 },
4609 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2819 },
4610 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 580 },
4611 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3648 },
4612 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4593 },
4613 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4594 },
4614 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4595 },
4615 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4596 },
4616 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4597 },
4617 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4598 },
4618 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
4619 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4599 },
4620 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 344 },
4621 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4600 },
4622 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4601 },
4623 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4602 },
4624 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 738 },
4625 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4603 },
4626 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 2268 },
4627 .{ .char = 'l', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4605 },
4628 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 568 },
4629 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4606 },
4630 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4607 },
4631 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 580 },
4632 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4608 },
4633 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 457 },
4634 .{ .char = 'q', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 286 },
4635 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4609 },
4636 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4610 },
4637 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4611 },
4638 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4612 },
4639 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4613 },
4640 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4614 },
4641 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 412 },
4642 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4261 },
4643 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 561 },
4644 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4615 },
4645 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3701 },
4646 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4616 },
4647 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4617 },
4648 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4261 },
4649 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4618 },
4650 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4619 },
4651 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4620 },
4652 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2199 },
4653 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4621 },
4654 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4622 },
4655 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4623 },
4656 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4624 },
4657 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3301 },
4658 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1129 },
4659 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4627 },
4660 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4628 },
4661 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 8, .child_index = 4632 },
4662 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4634 },
4663 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4635 },
4664 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4636 },
4665 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4637 },
4666 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4638 },
4667 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4639 },
4668 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4640 },
4669 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
4670 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4298 },
4671 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4642 },
4672 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4642 },
4673 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4301 },
4674 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4645 },
4675 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4646 },
4676 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4648 },
4677 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4649 },
4678 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4649 },
4679 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4649 },
4680 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4649 },
4681 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 28, .child_index = 4109 },
4682 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4649 },
4683 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4651 },
4684 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4649 },
4685 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4652 },
4686 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 28, .child_index = 4109 },
4687 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4317 },
4688 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4653 },
4689 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4654 },
4690 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 3547 },
4691 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4513 },
4692 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4693 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4516 },
4694 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
4695 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
4696 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 3807 },
4697 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4327 },
4698 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4656 },
4699 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4331 },
4700 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 9, .child_index = 4658 },
4701 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4660 },
4702 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4661 },
4703 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4662 },
4704 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4662 },
4705 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4295 },
4706 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4663 },
4707 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4663 },
4708 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4664 },
4709 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4667 },
4710 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4668 },
4711 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4668 },
4712 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4669 },
4713 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4670 },
4714 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4670 },
4715 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4716 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
4717 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4512 },
4718 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4346 },
4719 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4513 },
4720 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4513 },
4721 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3609 },
4722 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4671 },
4723 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4673 },
4724 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4674 },
4725 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4381 },
4726 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4675 },
4727 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4676 },
4728 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4546 },
4729 .{ .char = '0', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4730 .{ .char = '1', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4731 .{ .char = '2', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4732 .{ .char = '3', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4733 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 458 },
4734 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4677 },
4735 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4678 },
4736 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 1171 },
4737 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4679 },
4738 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4680 },
4739 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4681 },
4740 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4682 },
4741 .{ .char = 'C', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4683 },
4742 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4684 },
4743 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4685 },
4744 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4686 },
4745 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4687 },
4746 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4688 },
4747 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4689 },
4748 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3026 },
4749 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4690 },
4750 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4692 },
4751 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4207 },
4752 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3342 },
4753 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4693 },
4754 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 460 },
4755 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3470 },
4756 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4694 },
4757 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4695 },
4758 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4696 },
4759 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4697 },
4760 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4698 },
4761 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 460 },
4762 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4700 },
4763 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4701 },
4764 .{ .char = '3', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4702 },
4765 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4703 },
4766 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
4767 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4704 },
4768 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4705 },
4769 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4706 },
4770 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4707 },
4771 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4708 },
4772 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4709 },
4773 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4710 },
4774 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4711 },
4775 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4712 },
4776 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4713 },
4777 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4714 },
4778 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4715 },
4779 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4716 },
4780 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4717 },
4781 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4718 },
4782 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4719 },
4783 .{ .char = 's', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4784 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 664 },
4785 .{ .char = 'g', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 4720 },
4786 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4722 },
4787 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4723 },
4788 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4716 },
4789 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1663 },
4790 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4724 },
4791 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 585 },
4792 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4725 },
4793 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4726 },
4794 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 561 },
4795 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4727 },
4796 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4728 },
4797 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4730 },
4798 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4731 },
4799 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4732 },
4800 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4733 },
4801 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4734 },
4802 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4735 },
4803 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4736 },
4804 .{ .char = 'o', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4738 },
4805 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4739 },
4806 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4740 },
4807 .{ .char = 'c', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4741 },
4808 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4742 },
4809 .{ .char = 'h', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4743 },
4810 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4744 },
4811 .{ .char = '2', .end_of_word = false, .end_of_list = false, .number = 4, .child_index = 4745 },
4812 .{ .char = '3', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4745 },
4813 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4746 },
4814 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4747 },
4815 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4748 },
4816 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4636 },
4817 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4751 },
4818 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4752 },
4819 .{ .char = 'a', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4820 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4821 .{ .char = 'M', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4516 },
4822 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4823 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
4824 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4753 },
4825 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4301 },
4826 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4315 },
4827 .{ .char = 'M', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
4828 .{ .char = '_', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4754 },
4829 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4755 },
4830 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4756 },
4831 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4756 },
4832 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4757 },
4833 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4642 },
4834 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4642 },
4835 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4325 },
4836 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4540 },
4837 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4091 },
4838 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4138 },
4839 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4356 },
4840 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4524 },
4841 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4660 },
4842 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4758 },
4843 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4844 .{ .char = 'm', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4359 },
4845 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 655 },
4846 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4359 },
4847 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4759 },
4848 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4760 },
4849 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4762 },
4850 .{ .char = '3', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4763 },
4851 .{ .char = '6', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4764 },
4852 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4765 },
4853 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4766 },
4854 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4554 },
4855 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4767 },
4856 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4769 },
4857 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4554 },
4858 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 873 },
4859 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4560 },
4860 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 5, .child_index = 4773 },
4861 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4775 },
4862 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4776 },
4863 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4777 },
4864 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4778 },
4865 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4779 },
4866 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4780 },
4867 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4780 },
4868 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4781 },
4869 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 648 },
4870 .{ .char = '8', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4782 },
4871 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4783 },
4872 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 680 },
4873 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3659 },
4874 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4636 },
4875 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4784 },
4876 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2790 },
4877 .{ .char = '1', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 4785 },
4878 .{ .char = '2', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 4785 },
4879 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4786 },
4880 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 496 },
4881 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3941 },
4882 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4787 },
4883 .{ .char = 'c', .end_of_word = true, .end_of_list = true, .number = 3, .child_index = 4788 },
4884 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4789 },
4885 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4790 },
4886 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4791 },
4887 .{ .char = 'g', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 4792 },
4888 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4793 },
4889 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3342 },
4890 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4794 },
4891 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4289 },
4892 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4795 },
4893 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4796 },
4894 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4797 },
4895 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4798 },
4896 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4799 },
4897 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4800 },
4898 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2236 },
4899 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4801 },
4900 .{ .char = '2', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4901 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4802 },
4902 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4803 },
4903 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4804 },
4904 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4805 },
4905 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4806 },
4906 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4807 },
4907 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4469 },
4908 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4618 },
4909 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4469 },
4910 .{ .char = 'q', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4266 },
4911 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4808 },
4912 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4809 },
4913 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4810 },
4914 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4811 },
4915 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4812 },
4916 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4812 },
4917 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 4813 },
4918 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4814 },
4919 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4815 },
4920 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4816 },
4921 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4817 },
4922 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4818 },
4923 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4819 },
4924 .{ .char = 'D', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4820 },
4925 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4822 },
4926 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4207 },
4927 .{ .char = 'x', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4928 .{ .char = 'y', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4929 .{ .char = 'z', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4930 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4823 },
4931 .{ .char = '5', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4824 },
4932 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4301 },
4933 .{ .char = 'M', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4825 },
4934 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4651 },
4935 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4754 },
4936 .{ .char = 'x', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4077 },
4937 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4077 },
4938 .{ .char = 'M', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4359 },
4939 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4146 },
4940 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4146 },
4941 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4826 },
4942 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3268 },
4943 .{ .char = '4', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3268 },
4944 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4828 },
4945 .{ .char = 'k', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 1938 },
4946 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 458 },
4947 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4829 },
4948 .{ .char = 'w', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4949 .{ .char = 'x', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4950 .{ .char = 'y', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
4951 .{ .char = 'z', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4952 .{ .char = '6', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 649 },
4953 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4830 },
4954 .{ .char = 'e', .end_of_word = true, .end_of_list = true, .number = 6, .child_index = 4833 },
4955 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4837 },
4956 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4838 },
4957 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4839 },
4958 .{ .char = 'n', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 4840 },
4959 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 3886 },
4960 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4841 },
4961 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4842 },
4962 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4843 },
4963 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4844 },
4964 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4845 },
4965 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4846 },
4966 .{ .char = '1', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4847 },
4967 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4416 },
4968 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4210 },
4969 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4848 },
4970 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4849 },
4971 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4850 },
4972 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4851 },
4973 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 6, .child_index = 4852 },
4974 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4854 },
4975 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4855 },
4976 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4856 },
4977 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4857 },
4978 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4858 },
4979 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4859 },
4980 .{ .char = '0', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
4981 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4860 },
4982 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 4861 },
4983 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4862 },
4984 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4863 },
4985 .{ .char = 'j', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4864 },
4986 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4865 },
4987 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4867 },
4988 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4868 },
4989 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4869 },
4990 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4739 },
4991 .{ .char = 'd', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 4813 },
4992 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 291 },
4993 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4870 },
4994 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4871 },
4995 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4872 },
4996 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4873 },
4997 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4874 },
4998 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4873 },
4999 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4875 },
5000 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4875 },
5001 .{ .char = 'D', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4877 },
5002 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4880 },
5003 .{ .char = '1', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4881 },
5004 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4882 },
5005 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4757 },
5006 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4757 },
5007 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4884 },
5008 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4885 },
5009 .{ .char = 'a', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4886 },
5010 .{ .char = 'n', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 496 },
5011 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3366 },
5012 .{ .char = '1', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 648 },
5013 .{ .char = '6', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 649 },
5014 .{ .char = '8', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
5015 .{ .char = 'P', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4887 },
5016 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4888 },
5017 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4889 },
5018 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3052 },
5019 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4890 },
5020 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4891 },
5021 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2568 },
5022 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4892 },
5023 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2808 },
5024 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3026 },
5025 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4894 },
5026 .{ .char = '6', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3941 },
5027 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2790 },
5028 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4895 },
5029 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4896 },
5030 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3961 },
5031 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 3, .child_index = 4485 },
5032 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 3, .child_index = 4409 },
5033 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4897 },
5034 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4898 },
5035 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4899 },
5036 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
5037 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4900 },
5038 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4901 },
5039 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 471 },
5040 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4902 },
5041 .{ .char = 'b', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4903 },
5042 .{ .char = 'z', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4904 },
5043 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4905 },
5044 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 2, .child_index = 4906 },
5045 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 4906 },
5046 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4907 },
5047 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2877 },
5048 .{ .char = 'f', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4908 },
5049 .{ .char = 'p', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 4813 },
5050 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 183 },
5051 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4909 },
5052 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4910 },
5053 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4911 },
5054 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4912 },
5055 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4912 },
5056 .{ .char = 'f', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4912 },
5057 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4912 },
5058 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4913 },
5059 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4693 },
5060 .{ .char = '2', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4914 },
5061 .{ .char = 'M', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 655 },
5062 .{ .char = 'l', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
5063 .{ .char = 'g', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4916 },
5064 .{ .char = 's', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4917 },
5065 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4918 },
5066 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4919 },
5067 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4920 },
5068 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 4, .child_index = 4921 },
5069 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2963 },
5070 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4925 },
5071 .{ .char = 'i', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 3026 },
5072 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3026 },
5073 .{ .char = 'm', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4926 },
5074 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3366 },
5075 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 311 },
5076 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4927 },
5077 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4928 },
5078 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 451 },
5079 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4929 },
5080 .{ .char = 'c', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4930 },
5081 .{ .char = 'v', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 323 },
5082 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4931 },
5083 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4932 },
5084 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4017 },
5085 .{ .char = 'a', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
5086 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4933 },
5087 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4934 },
5088 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4935 },
5089 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4913 },
5090 .{ .char = 'h', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4936 },
5091 .{ .char = '_', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
5092 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4912 },
5093 .{ .char = 'l', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
5094 .{ .char = 'u', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
5095 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4937 },
5096 .{ .char = 'k', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4938 },
5097 .{ .char = 'q', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
5098 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4939 },
5099 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4940 },
5100 .{ .char = 'b', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4941 },
5101 .{ .char = 'p', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4587 },
5102 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 520 },
5103 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 420 },
5104 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4942 },
5105 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4943 },
5106 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4944 },
5107 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4945 },
5108 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3301 },
5109 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4946 },
5110 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4947 },
5111 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3195 },
5112 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4948 },
5113 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2460 },
5114 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4949 },
5115 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4913 },
5116 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4950 },
5117 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 5, .child_index = 4952 },
5118 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4955 },
5119 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4956 },
5120 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4957 },
5121 .{ .char = '1', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
5122 .{ .char = 'n', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4958 },
5123 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 3578 },
5124 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 457 },
5125 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 2230 },
5126 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4959 },
5127 .{ .char = 'u', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 572 },
5128 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4960 },
5129 .{ .char = 's', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4961 },
5130 .{ .char = 'w', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 821 },
5131 .{ .char = 'e', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4918 },
5132 .{ .char = 'g', .end_of_word = false, .end_of_list = false, .number = 2, .child_index = 4962 },
5133 .{ .char = 'l', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4962 },
5134 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4964 },
5135 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4965 },
5136 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4966 },
5137 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4207 },
5138 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 450 },
5139 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4967 },
5140 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4969 },
5141 .{ .char = 'e', .end_of_word = true, .end_of_list = false, .number = 1, .child_index = 0 },
5142 .{ .char = 't', .end_of_word = true, .end_of_list = true, .number = 1, .child_index = 0 },
5143 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 2, .child_index = 4970 },
5144 .{ .char = 'S', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4971 },
5145 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4972 },
5146 .{ .char = 'd', .end_of_word = false, .end_of_list = false, .number = 1, .child_index = 4973 },
5147 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4974 },
5148 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1440 },
5149 .{ .char = 'r', .end_of_word = true, .end_of_list = true, .number = 2, .child_index = 4975 },
5150 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4976 },
5151 .{ .char = 'o', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 654 },
5152 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4977 },
5153 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4978 },
5154 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 459 },
5155 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4979 },
5156 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4980 },
5157 .{ .char = 'd', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4981 },
5158 .{ .char = 'i', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 1701 },
5159 .{ .char = 'a', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4982 },
5160 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4983 },
5161 .{ .char = '_', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4984 },
5162 .{ .char = 'r', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4913 },
5163 .{ .char = 't', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4985 },
5164 .{ .char = 'y', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4986 },
5165 .{ .char = 'p', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4987 },
5166 .{ .char = 'e', .end_of_word = false, .end_of_list = true, .number = 1, .child_index = 4913 },
5167};
5168pub const data = blk: {
5169 @setEvalBranchQuota(27902);
5170 break :blk [_]@This(){
5171 // _Block_object_assign
5172 .{ .tag = @enumFromInt(0), .properties = .{ .param_str = "vv*vC*iC", .header = .blocks, .attributes = .{ .lib_function_without_prefix = true } } },
5173 // _Block_object_dispose
5174 .{ .tag = @enumFromInt(1), .properties = .{ .param_str = "vvC*iC", .header = .blocks, .attributes = .{ .lib_function_without_prefix = true } } },
5175 // _Exit
5176 .{ .tag = @enumFromInt(2), .properties = .{ .param_str = "vi", .header = .stdlib, .attributes = .{ .noreturn = true, .lib_function_without_prefix = true } } },
5177 // _InterlockedAnd
5178 .{ .tag = @enumFromInt(3), .properties = .{ .param_str = "NiNiD*Ni", .language = .all_ms_languages } },
5179 // _InterlockedAnd16
5180 .{ .tag = @enumFromInt(4), .properties = .{ .param_str = "ssD*s", .language = .all_ms_languages } },
5181 // _InterlockedAnd8
5182 .{ .tag = @enumFromInt(5), .properties = .{ .param_str = "ccD*c", .language = .all_ms_languages } },
5183 // _InterlockedCompareExchange
5184 .{ .tag = @enumFromInt(6), .properties = .{ .param_str = "NiNiD*NiNi", .language = .all_ms_languages } },
5185 // _InterlockedCompareExchange16
5186 .{ .tag = @enumFromInt(7), .properties = .{ .param_str = "ssD*ss", .language = .all_ms_languages } },
5187 // _InterlockedCompareExchange64
5188 .{ .tag = @enumFromInt(8), .properties = .{ .param_str = "LLiLLiD*LLiLLi", .language = .all_ms_languages } },
5189 // _InterlockedCompareExchange8
5190 .{ .tag = @enumFromInt(9), .properties = .{ .param_str = "ccD*cc", .language = .all_ms_languages } },
5191 // _InterlockedCompareExchangePointer
5192 .{ .tag = @enumFromInt(10), .properties = .{ .param_str = "v*v*D*v*v*", .language = .all_ms_languages } },
5193 // _InterlockedCompareExchangePointer_nf
5194 .{ .tag = @enumFromInt(11), .properties = .{ .param_str = "v*v*D*v*v*", .language = .all_ms_languages } },
5195 // _InterlockedDecrement
5196 .{ .tag = @enumFromInt(12), .properties = .{ .param_str = "NiNiD*", .language = .all_ms_languages } },
5197 // _InterlockedDecrement16
5198 .{ .tag = @enumFromInt(13), .properties = .{ .param_str = "ssD*", .language = .all_ms_languages } },
5199 // _InterlockedExchange
5200 .{ .tag = @enumFromInt(14), .properties = .{ .param_str = "NiNiD*Ni", .language = .all_ms_languages } },
5201 // _InterlockedExchange16
5202 .{ .tag = @enumFromInt(15), .properties = .{ .param_str = "ssD*s", .language = .all_ms_languages } },
5203 // _InterlockedExchange8
5204 .{ .tag = @enumFromInt(16), .properties = .{ .param_str = "ccD*c", .language = .all_ms_languages } },
5205 // _InterlockedExchangeAdd
5206 .{ .tag = @enumFromInt(17), .properties = .{ .param_str = "NiNiD*Ni", .language = .all_ms_languages } },
5207 // _InterlockedExchangeAdd16
5208 .{ .tag = @enumFromInt(18), .properties = .{ .param_str = "ssD*s", .language = .all_ms_languages } },
5209 // _InterlockedExchangeAdd8
5210 .{ .tag = @enumFromInt(19), .properties = .{ .param_str = "ccD*c", .language = .all_ms_languages } },
5211 // _InterlockedExchangePointer
5212 .{ .tag = @enumFromInt(20), .properties = .{ .param_str = "v*v*D*v*", .language = .all_ms_languages } },
5213 // _InterlockedExchangeSub
5214 .{ .tag = @enumFromInt(21), .properties = .{ .param_str = "NiNiD*Ni", .language = .all_ms_languages } },
5215 // _InterlockedExchangeSub16
5216 .{ .tag = @enumFromInt(22), .properties = .{ .param_str = "ssD*s", .language = .all_ms_languages } },
5217 // _InterlockedExchangeSub8
5218 .{ .tag = @enumFromInt(23), .properties = .{ .param_str = "ccD*c", .language = .all_ms_languages } },
5219 // _InterlockedIncrement
5220 .{ .tag = @enumFromInt(24), .properties = .{ .param_str = "NiNiD*", .language = .all_ms_languages } },
5221 // _InterlockedIncrement16
5222 .{ .tag = @enumFromInt(25), .properties = .{ .param_str = "ssD*", .language = .all_ms_languages } },
5223 // _InterlockedOr
5224 .{ .tag = @enumFromInt(26), .properties = .{ .param_str = "NiNiD*Ni", .language = .all_ms_languages } },
5225 // _InterlockedOr16
5226 .{ .tag = @enumFromInt(27), .properties = .{ .param_str = "ssD*s", .language = .all_ms_languages } },
5227 // _InterlockedOr8
5228 .{ .tag = @enumFromInt(28), .properties = .{ .param_str = "ccD*c", .language = .all_ms_languages } },
5229 // _InterlockedXor
5230 .{ .tag = @enumFromInt(29), .properties = .{ .param_str = "NiNiD*Ni", .language = .all_ms_languages } },
5231 // _InterlockedXor16
5232 .{ .tag = @enumFromInt(30), .properties = .{ .param_str = "ssD*s", .language = .all_ms_languages } },
5233 // _InterlockedXor8
5234 .{ .tag = @enumFromInt(31), .properties = .{ .param_str = "ccD*c", .language = .all_ms_languages } },
5235 // _MoveFromCoprocessor
5236 .{ .tag = @enumFromInt(32), .properties = .{ .param_str = "UiIUiIUiIUiIUiIUi", .language = .all_ms_languages, .target_set = TargetSet.initOne(.arm) } },
5237 // _MoveFromCoprocessor2
5238 .{ .tag = @enumFromInt(33), .properties = .{ .param_str = "UiIUiIUiIUiIUiIUi", .language = .all_ms_languages, .target_set = TargetSet.initOne(.arm) } },
5239 // _MoveToCoprocessor
5240 .{ .tag = @enumFromInt(34), .properties = .{ .param_str = "vUiIUiIUiIUiIUiIUi", .language = .all_ms_languages, .target_set = TargetSet.initOne(.arm) } },
5241 // _MoveToCoprocessor2
5242 .{ .tag = @enumFromInt(35), .properties = .{ .param_str = "vUiIUiIUiIUiIUiIUi", .language = .all_ms_languages, .target_set = TargetSet.initOne(.arm) } },
5243 // _ReturnAddress
5244 .{ .tag = @enumFromInt(36), .properties = .{ .param_str = "v*", .language = .all_ms_languages } },
5245 // __GetExceptionInfo
5246 .{ .tag = @enumFromInt(37), .properties = .{ .param_str = "v*.", .language = .all_ms_languages, .attributes = .{ .custom_typecheck = true, .eval_args = false } } },
5247 // __abnormal_termination
5248 .{ .tag = @enumFromInt(38), .properties = .{ .param_str = "i", .language = .all_ms_languages } },
5249 // __annotation
5250 .{ .tag = @enumFromInt(39), .properties = .{ .param_str = "wC*.", .language = .all_ms_languages } },
5251 // __arithmetic_fence
5252 .{ .tag = @enumFromInt(40), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true, .const_evaluable = true } } },
5253 // __assume
5254 .{ .tag = @enumFromInt(41), .properties = .{ .param_str = "vb", .language = .all_ms_languages, .attributes = .{ .const_evaluable = true } } },
5255 // __atomic_add_fetch
5256 .{ .tag = @enumFromInt(42), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5257 // __atomic_always_lock_free
5258 .{ .tag = @enumFromInt(43), .properties = .{ .param_str = "bzvCD*", .attributes = .{ .const_evaluable = true } } },
5259 // __atomic_and_fetch
5260 .{ .tag = @enumFromInt(44), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5261 // __atomic_clear
5262 .{ .tag = @enumFromInt(45), .properties = .{ .param_str = "vvD*i" } },
5263 // __atomic_compare_exchange
5264 .{ .tag = @enumFromInt(46), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5265 // __atomic_compare_exchange_n
5266 .{ .tag = @enumFromInt(47), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5267 // __atomic_exchange
5268 .{ .tag = @enumFromInt(48), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5269 // __atomic_exchange_n
5270 .{ .tag = @enumFromInt(49), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5271 // __atomic_fetch_add
5272 .{ .tag = @enumFromInt(50), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5273 // __atomic_fetch_and
5274 .{ .tag = @enumFromInt(51), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5275 // __atomic_fetch_max
5276 .{ .tag = @enumFromInt(52), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5277 // __atomic_fetch_min
5278 .{ .tag = @enumFromInt(53), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5279 // __atomic_fetch_nand
5280 .{ .tag = @enumFromInt(54), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5281 // __atomic_fetch_or
5282 .{ .tag = @enumFromInt(55), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5283 // __atomic_fetch_sub
5284 .{ .tag = @enumFromInt(56), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5285 // __atomic_fetch_xor
5286 .{ .tag = @enumFromInt(57), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5287 // __atomic_is_lock_free
5288 .{ .tag = @enumFromInt(58), .properties = .{ .param_str = "bzvCD*", .attributes = .{ .const_evaluable = true } } },
5289 // __atomic_load
5290 .{ .tag = @enumFromInt(59), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5291 // __atomic_load_n
5292 .{ .tag = @enumFromInt(60), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5293 // __atomic_max_fetch
5294 .{ .tag = @enumFromInt(61), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5295 // __atomic_min_fetch
5296 .{ .tag = @enumFromInt(62), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5297 // __atomic_nand_fetch
5298 .{ .tag = @enumFromInt(63), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5299 // __atomic_or_fetch
5300 .{ .tag = @enumFromInt(64), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5301 // __atomic_signal_fence
5302 .{ .tag = @enumFromInt(65), .properties = .{ .param_str = "vi" } },
5303 // __atomic_store
5304 .{ .tag = @enumFromInt(66), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5305 // __atomic_store_n
5306 .{ .tag = @enumFromInt(67), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5307 // __atomic_sub_fetch
5308 .{ .tag = @enumFromInt(68), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5309 // __atomic_test_and_set
5310 .{ .tag = @enumFromInt(69), .properties = .{ .param_str = "bvD*i" } },
5311 // __atomic_thread_fence
5312 .{ .tag = @enumFromInt(70), .properties = .{ .param_str = "vi" } },
5313 // __atomic_xor_fetch
5314 .{ .tag = @enumFromInt(71), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5315 // __builtin___CFStringMakeConstantString
5316 .{ .tag = @enumFromInt(72), .properties = .{ .param_str = "FC*cC*", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
5317 // __builtin___NSStringMakeConstantString
5318 .{ .tag = @enumFromInt(73), .properties = .{ .param_str = "FC*cC*", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
5319 // __builtin___clear_cache
5320 .{ .tag = @enumFromInt(74), .properties = .{ .param_str = "vc*c*" } },
5321 // __builtin___fprintf_chk
5322 .{ .tag = @enumFromInt(75), .properties = .{ .param_str = "iP*RicC*R.", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .printf, .format_string_position = 2 } } },
5323 // __builtin___get_unsafe_stack_bottom
5324 .{ .tag = @enumFromInt(76), .properties = .{ .param_str = "v*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5325 // __builtin___get_unsafe_stack_ptr
5326 .{ .tag = @enumFromInt(77), .properties = .{ .param_str = "v*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5327 // __builtin___get_unsafe_stack_start
5328 .{ .tag = @enumFromInt(78), .properties = .{ .param_str = "v*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5329 // __builtin___get_unsafe_stack_top
5330 .{ .tag = @enumFromInt(79), .properties = .{ .param_str = "v*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5331 // __builtin___memccpy_chk
5332 .{ .tag = @enumFromInt(80), .properties = .{ .param_str = "v*v*vC*izz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5333 // __builtin___memcpy_chk
5334 .{ .tag = @enumFromInt(81), .properties = .{ .param_str = "v*v*vC*zz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5335 // __builtin___memmove_chk
5336 .{ .tag = @enumFromInt(82), .properties = .{ .param_str = "v*v*vC*zz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5337 // __builtin___mempcpy_chk
5338 .{ .tag = @enumFromInt(83), .properties = .{ .param_str = "v*v*vC*zz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5339 // __builtin___memset_chk
5340 .{ .tag = @enumFromInt(84), .properties = .{ .param_str = "v*v*izz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5341 // __builtin___printf_chk
5342 .{ .tag = @enumFromInt(85), .properties = .{ .param_str = "iicC*R.", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .printf, .format_string_position = 1 } } },
5343 // __builtin___snprintf_chk
5344 .{ .tag = @enumFromInt(86), .properties = .{ .param_str = "ic*RzizcC*R.", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .printf, .format_string_position = 4 } } },
5345 // __builtin___sprintf_chk
5346 .{ .tag = @enumFromInt(87), .properties = .{ .param_str = "ic*RizcC*R.", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .printf, .format_string_position = 3 } } },
5347 // __builtin___stpcpy_chk
5348 .{ .tag = @enumFromInt(88), .properties = .{ .param_str = "c*c*cC*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5349 // __builtin___stpncpy_chk
5350 .{ .tag = @enumFromInt(89), .properties = .{ .param_str = "c*c*cC*zz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5351 // __builtin___strcat_chk
5352 .{ .tag = @enumFromInt(90), .properties = .{ .param_str = "c*c*cC*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5353 // __builtin___strcpy_chk
5354 .{ .tag = @enumFromInt(91), .properties = .{ .param_str = "c*c*cC*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5355 // __builtin___strlcat_chk
5356 .{ .tag = @enumFromInt(92), .properties = .{ .param_str = "zc*cC*zz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5357 // __builtin___strlcpy_chk
5358 .{ .tag = @enumFromInt(93), .properties = .{ .param_str = "zc*cC*zz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5359 // __builtin___strncat_chk
5360 .{ .tag = @enumFromInt(94), .properties = .{ .param_str = "c*c*cC*zz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5361 // __builtin___strncpy_chk
5362 .{ .tag = @enumFromInt(95), .properties = .{ .param_str = "c*c*cC*zz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5363 // __builtin___vfprintf_chk
5364 .{ .tag = @enumFromInt(96), .properties = .{ .param_str = "iP*RicC*Ra", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .vprintf, .format_string_position = 2 } } },
5365 // __builtin___vprintf_chk
5366 .{ .tag = @enumFromInt(97), .properties = .{ .param_str = "iicC*Ra", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .vprintf, .format_string_position = 1 } } },
5367 // __builtin___vsnprintf_chk
5368 .{ .tag = @enumFromInt(98), .properties = .{ .param_str = "ic*RzizcC*Ra", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .vprintf, .format_string_position = 4 } } },
5369 // __builtin___vsprintf_chk
5370 .{ .tag = @enumFromInt(99), .properties = .{ .param_str = "ic*RizcC*Ra", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .vprintf, .format_string_position = 3 } } },
5371 // __builtin_abort
5372 .{ .tag = @enumFromInt(100), .properties = .{ .param_str = "v", .attributes = .{ .noreturn = true, .lib_function_with_builtin_prefix = true } } },
5373 // __builtin_abs
5374 .{ .tag = @enumFromInt(101), .properties = .{ .param_str = "ii", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
5375 // __builtin_acos
5376 .{ .tag = @enumFromInt(102), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5377 // __builtin_acosf
5378 .{ .tag = @enumFromInt(103), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5379 // __builtin_acosf128
5380 .{ .tag = @enumFromInt(104), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5381 // __builtin_acosh
5382 .{ .tag = @enumFromInt(105), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5383 // __builtin_acoshf
5384 .{ .tag = @enumFromInt(106), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5385 // __builtin_acoshf128
5386 .{ .tag = @enumFromInt(107), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5387 // __builtin_acoshl
5388 .{ .tag = @enumFromInt(108), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5389 // __builtin_acosl
5390 .{ .tag = @enumFromInt(109), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5391 // __builtin_add_overflow
5392 .{ .tag = @enumFromInt(110), .properties = .{ .param_str = "b.", .attributes = .{ .custom_typecheck = true, .const_evaluable = true } } },
5393 // __builtin_addc
5394 .{ .tag = @enumFromInt(111), .properties = .{ .param_str = "UiUiCUiCUiCUi*" } },
5395 // __builtin_addcb
5396 .{ .tag = @enumFromInt(112), .properties = .{ .param_str = "UcUcCUcCUcCUc*" } },
5397 // __builtin_addcl
5398 .{ .tag = @enumFromInt(113), .properties = .{ .param_str = "ULiULiCULiCULiCULi*" } },
5399 // __builtin_addcll
5400 .{ .tag = @enumFromInt(114), .properties = .{ .param_str = "ULLiULLiCULLiCULLiCULLi*" } },
5401 // __builtin_addcs
5402 .{ .tag = @enumFromInt(115), .properties = .{ .param_str = "UsUsCUsCUsCUs*" } },
5403 // __builtin_align_down
5404 .{ .tag = @enumFromInt(116), .properties = .{ .param_str = "v*vC*z", .attributes = .{ .@"const" = true, .custom_typecheck = true, .const_evaluable = true } } },
5405 // __builtin_align_up
5406 .{ .tag = @enumFromInt(117), .properties = .{ .param_str = "v*vC*z", .attributes = .{ .@"const" = true, .custom_typecheck = true, .const_evaluable = true } } },
5407 // __builtin_alloca
5408 .{ .tag = @enumFromInt(118), .properties = .{ .param_str = "v*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5409 // __builtin_alloca_uninitialized
5410 .{ .tag = @enumFromInt(119), .properties = .{ .param_str = "v*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5411 // __builtin_alloca_with_align
5412 .{ .tag = @enumFromInt(120), .properties = .{ .param_str = "v*zIz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5413 // __builtin_alloca_with_align_uninitialized
5414 .{ .tag = @enumFromInt(121), .properties = .{ .param_str = "v*zIz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5415 // __builtin_amdgcn_alignbit
5416 .{ .tag = @enumFromInt(122), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5417 // __builtin_amdgcn_alignbyte
5418 .{ .tag = @enumFromInt(123), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5419 // __builtin_amdgcn_atomic_dec32
5420 .{ .tag = @enumFromInt(124), .properties = .{ .param_str = "UZiUZiD*UZiUicC*", .target_set = TargetSet.initOne(.amdgpu) } },
5421 // __builtin_amdgcn_atomic_dec64
5422 .{ .tag = @enumFromInt(125), .properties = .{ .param_str = "UWiUWiD*UWiUicC*", .target_set = TargetSet.initOne(.amdgpu) } },
5423 // __builtin_amdgcn_atomic_inc32
5424 .{ .tag = @enumFromInt(126), .properties = .{ .param_str = "UZiUZiD*UZiUicC*", .target_set = TargetSet.initOne(.amdgpu) } },
5425 // __builtin_amdgcn_atomic_inc64
5426 .{ .tag = @enumFromInt(127), .properties = .{ .param_str = "UWiUWiD*UWiUicC*", .target_set = TargetSet.initOne(.amdgpu) } },
5427 // __builtin_amdgcn_buffer_wbinvl1
5428 .{ .tag = @enumFromInt(128), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.amdgpu) } },
5429 // __builtin_amdgcn_class
5430 .{ .tag = @enumFromInt(129), .properties = .{ .param_str = "bdi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5431 // __builtin_amdgcn_classf
5432 .{ .tag = @enumFromInt(130), .properties = .{ .param_str = "bfi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5433 // __builtin_amdgcn_cosf
5434 .{ .tag = @enumFromInt(131), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5435 // __builtin_amdgcn_cubeid
5436 .{ .tag = @enumFromInt(132), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5437 // __builtin_amdgcn_cubema
5438 .{ .tag = @enumFromInt(133), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5439 // __builtin_amdgcn_cubesc
5440 .{ .tag = @enumFromInt(134), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5441 // __builtin_amdgcn_cubetc
5442 .{ .tag = @enumFromInt(135), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5443 // __builtin_amdgcn_cvt_pk_i16
5444 .{ .tag = @enumFromInt(136), .properties = .{ .param_str = "E2sii", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5445 // __builtin_amdgcn_cvt_pk_u16
5446 .{ .tag = @enumFromInt(137), .properties = .{ .param_str = "E2UsUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5447 // __builtin_amdgcn_cvt_pk_u8_f32
5448 .{ .tag = @enumFromInt(138), .properties = .{ .param_str = "UifUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5449 // __builtin_amdgcn_cvt_pknorm_i16
5450 .{ .tag = @enumFromInt(139), .properties = .{ .param_str = "E2sff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5451 // __builtin_amdgcn_cvt_pknorm_u16
5452 .{ .tag = @enumFromInt(140), .properties = .{ .param_str = "E2Usff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5453 // __builtin_amdgcn_cvt_pkrtz
5454 .{ .tag = @enumFromInt(141), .properties = .{ .param_str = "E2hff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5455 // __builtin_amdgcn_dispatch_ptr
5456 .{ .tag = @enumFromInt(142), .properties = .{ .param_str = "v*4", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5457 // __builtin_amdgcn_div_fixup
5458 .{ .tag = @enumFromInt(143), .properties = .{ .param_str = "dddd", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5459 // __builtin_amdgcn_div_fixupf
5460 .{ .tag = @enumFromInt(144), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5461 // __builtin_amdgcn_div_fmas
5462 .{ .tag = @enumFromInt(145), .properties = .{ .param_str = "ddddb", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5463 // __builtin_amdgcn_div_fmasf
5464 .{ .tag = @enumFromInt(146), .properties = .{ .param_str = "ffffb", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5465 // __builtin_amdgcn_div_scale
5466 .{ .tag = @enumFromInt(147), .properties = .{ .param_str = "dddbb*", .target_set = TargetSet.initOne(.amdgpu) } },
5467 // __builtin_amdgcn_div_scalef
5468 .{ .tag = @enumFromInt(148), .properties = .{ .param_str = "fffbb*", .target_set = TargetSet.initOne(.amdgpu) } },
5469 // __builtin_amdgcn_ds_append
5470 .{ .tag = @enumFromInt(149), .properties = .{ .param_str = "ii*3", .target_set = TargetSet.initOne(.amdgpu) } },
5471 // __builtin_amdgcn_ds_bpermute
5472 .{ .tag = @enumFromInt(150), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5473 // __builtin_amdgcn_ds_consume
5474 .{ .tag = @enumFromInt(151), .properties = .{ .param_str = "ii*3", .target_set = TargetSet.initOne(.amdgpu) } },
5475 // __builtin_amdgcn_ds_faddf
5476 .{ .tag = @enumFromInt(152), .properties = .{ .param_str = "ff*3fIiIiIb", .target_set = TargetSet.initOne(.amdgpu) } },
5477 // __builtin_amdgcn_ds_fmaxf
5478 .{ .tag = @enumFromInt(153), .properties = .{ .param_str = "ff*3fIiIiIb", .target_set = TargetSet.initOne(.amdgpu) } },
5479 // __builtin_amdgcn_ds_fminf
5480 .{ .tag = @enumFromInt(154), .properties = .{ .param_str = "ff*3fIiIiIb", .target_set = TargetSet.initOne(.amdgpu) } },
5481 // __builtin_amdgcn_ds_permute
5482 .{ .tag = @enumFromInt(155), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5483 // __builtin_amdgcn_ds_swizzle
5484 .{ .tag = @enumFromInt(156), .properties = .{ .param_str = "iiIi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5485 // __builtin_amdgcn_endpgm
5486 .{ .tag = @enumFromInt(157), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .noreturn = true } } },
5487 // __builtin_amdgcn_exp2f
5488 .{ .tag = @enumFromInt(158), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5489 // __builtin_amdgcn_fcmp
5490 .{ .tag = @enumFromInt(159), .properties = .{ .param_str = "WUiddIi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5491 // __builtin_amdgcn_fcmpf
5492 .{ .tag = @enumFromInt(160), .properties = .{ .param_str = "WUiffIi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5493 // __builtin_amdgcn_fence
5494 .{ .tag = @enumFromInt(161), .properties = .{ .param_str = "vUicC*", .target_set = TargetSet.initOne(.amdgpu) } },
5495 // __builtin_amdgcn_fmed3f
5496 .{ .tag = @enumFromInt(162), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5497 // __builtin_amdgcn_fract
5498 .{ .tag = @enumFromInt(163), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5499 // __builtin_amdgcn_fractf
5500 .{ .tag = @enumFromInt(164), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5501 // __builtin_amdgcn_frexp_exp
5502 .{ .tag = @enumFromInt(165), .properties = .{ .param_str = "id", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5503 // __builtin_amdgcn_frexp_expf
5504 .{ .tag = @enumFromInt(166), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5505 // __builtin_amdgcn_frexp_mant
5506 .{ .tag = @enumFromInt(167), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5507 // __builtin_amdgcn_frexp_mantf
5508 .{ .tag = @enumFromInt(168), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5509 // __builtin_amdgcn_grid_size_x
5510 .{ .tag = @enumFromInt(169), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5511 // __builtin_amdgcn_grid_size_y
5512 .{ .tag = @enumFromInt(170), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5513 // __builtin_amdgcn_grid_size_z
5514 .{ .tag = @enumFromInt(171), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5515 // __builtin_amdgcn_groupstaticsize
5516 .{ .tag = @enumFromInt(172), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu) } },
5517 // __builtin_amdgcn_iglp_opt
5518 .{ .tag = @enumFromInt(173), .properties = .{ .param_str = "vIi", .target_set = TargetSet.initOne(.amdgpu) } },
5519 // __builtin_amdgcn_implicitarg_ptr
5520 .{ .tag = @enumFromInt(174), .properties = .{ .param_str = "v*4", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5521 // __builtin_amdgcn_interp_mov
5522 .{ .tag = @enumFromInt(175), .properties = .{ .param_str = "fUiUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5523 // __builtin_amdgcn_interp_p1
5524 .{ .tag = @enumFromInt(176), .properties = .{ .param_str = "ffUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5525 // __builtin_amdgcn_interp_p1_f16
5526 .{ .tag = @enumFromInt(177), .properties = .{ .param_str = "ffUiUibUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5527 // __builtin_amdgcn_interp_p2
5528 .{ .tag = @enumFromInt(178), .properties = .{ .param_str = "fffUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5529 // __builtin_amdgcn_interp_p2_f16
5530 .{ .tag = @enumFromInt(179), .properties = .{ .param_str = "hffUiUibUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5531 // __builtin_amdgcn_is_private
5532 .{ .tag = @enumFromInt(180), .properties = .{ .param_str = "bvC*0", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5533 // __builtin_amdgcn_is_shared
5534 .{ .tag = @enumFromInt(181), .properties = .{ .param_str = "bvC*0", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5535 // __builtin_amdgcn_kernarg_segment_ptr
5536 .{ .tag = @enumFromInt(182), .properties = .{ .param_str = "v*4", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5537 // __builtin_amdgcn_ldexp
5538 .{ .tag = @enumFromInt(183), .properties = .{ .param_str = "ddi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5539 // __builtin_amdgcn_ldexpf
5540 .{ .tag = @enumFromInt(184), .properties = .{ .param_str = "ffi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5541 // __builtin_amdgcn_lerp
5542 .{ .tag = @enumFromInt(185), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5543 // __builtin_amdgcn_log_clampf
5544 .{ .tag = @enumFromInt(186), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5545 // __builtin_amdgcn_logf
5546 .{ .tag = @enumFromInt(187), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5547 // __builtin_amdgcn_mbcnt_hi
5548 .{ .tag = @enumFromInt(188), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5549 // __builtin_amdgcn_mbcnt_lo
5550 .{ .tag = @enumFromInt(189), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5551 // __builtin_amdgcn_mqsad_pk_u16_u8
5552 .{ .tag = @enumFromInt(190), .properties = .{ .param_str = "WUiWUiUiWUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5553 // __builtin_amdgcn_mqsad_u32_u8
5554 .{ .tag = @enumFromInt(191), .properties = .{ .param_str = "V4UiWUiUiV4Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5555 // __builtin_amdgcn_msad_u8
5556 .{ .tag = @enumFromInt(192), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5557 // __builtin_amdgcn_qsad_pk_u16_u8
5558 .{ .tag = @enumFromInt(193), .properties = .{ .param_str = "WUiWUiUiWUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5559 // __builtin_amdgcn_queue_ptr
5560 .{ .tag = @enumFromInt(194), .properties = .{ .param_str = "v*4", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5561 // __builtin_amdgcn_rcp
5562 .{ .tag = @enumFromInt(195), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5563 // __builtin_amdgcn_rcpf
5564 .{ .tag = @enumFromInt(196), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5565 // __builtin_amdgcn_read_exec
5566 .{ .tag = @enumFromInt(197), .properties = .{ .param_str = "WUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5567 // __builtin_amdgcn_read_exec_hi
5568 .{ .tag = @enumFromInt(198), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5569 // __builtin_amdgcn_read_exec_lo
5570 .{ .tag = @enumFromInt(199), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5571 // __builtin_amdgcn_readfirstlane
5572 .{ .tag = @enumFromInt(200), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5573 // __builtin_amdgcn_readlane
5574 .{ .tag = @enumFromInt(201), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5575 // __builtin_amdgcn_rsq
5576 .{ .tag = @enumFromInt(202), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5577 // __builtin_amdgcn_rsq_clamp
5578 .{ .tag = @enumFromInt(203), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5579 // __builtin_amdgcn_rsq_clampf
5580 .{ .tag = @enumFromInt(204), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5581 // __builtin_amdgcn_rsqf
5582 .{ .tag = @enumFromInt(205), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5583 // __builtin_amdgcn_s_barrier
5584 .{ .tag = @enumFromInt(206), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.amdgpu) } },
5585 // __builtin_amdgcn_s_dcache_inv
5586 .{ .tag = @enumFromInt(207), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.amdgpu) } },
5587 // __builtin_amdgcn_s_decperflevel
5588 .{ .tag = @enumFromInt(208), .properties = .{ .param_str = "vIi", .target_set = TargetSet.initOne(.amdgpu) } },
5589 // __builtin_amdgcn_s_getpc
5590 .{ .tag = @enumFromInt(209), .properties = .{ .param_str = "WUi", .target_set = TargetSet.initOne(.amdgpu) } },
5591 // __builtin_amdgcn_s_getreg
5592 .{ .tag = @enumFromInt(210), .properties = .{ .param_str = "UiIi", .target_set = TargetSet.initOne(.amdgpu) } },
5593 // __builtin_amdgcn_s_incperflevel
5594 .{ .tag = @enumFromInt(211), .properties = .{ .param_str = "vIi", .target_set = TargetSet.initOne(.amdgpu) } },
5595 // __builtin_amdgcn_s_sendmsg
5596 .{ .tag = @enumFromInt(212), .properties = .{ .param_str = "vIiUi", .target_set = TargetSet.initOne(.amdgpu) } },
5597 // __builtin_amdgcn_s_sendmsghalt
5598 .{ .tag = @enumFromInt(213), .properties = .{ .param_str = "vIiUi", .target_set = TargetSet.initOne(.amdgpu) } },
5599 // __builtin_amdgcn_s_setprio
5600 .{ .tag = @enumFromInt(214), .properties = .{ .param_str = "vIs", .target_set = TargetSet.initOne(.amdgpu) } },
5601 // __builtin_amdgcn_s_setreg
5602 .{ .tag = @enumFromInt(215), .properties = .{ .param_str = "vIiUi", .target_set = TargetSet.initOne(.amdgpu) } },
5603 // __builtin_amdgcn_s_sleep
5604 .{ .tag = @enumFromInt(216), .properties = .{ .param_str = "vIi", .target_set = TargetSet.initOne(.amdgpu) } },
5605 // __builtin_amdgcn_s_waitcnt
5606 .{ .tag = @enumFromInt(217), .properties = .{ .param_str = "vIi", .target_set = TargetSet.initOne(.amdgpu) } },
5607 // __builtin_amdgcn_sad_hi_u8
5608 .{ .tag = @enumFromInt(218), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5609 // __builtin_amdgcn_sad_u16
5610 .{ .tag = @enumFromInt(219), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5611 // __builtin_amdgcn_sad_u8
5612 .{ .tag = @enumFromInt(220), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5613 // __builtin_amdgcn_sbfe
5614 .{ .tag = @enumFromInt(221), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5615 // __builtin_amdgcn_sched_barrier
5616 .{ .tag = @enumFromInt(222), .properties = .{ .param_str = "vIi", .target_set = TargetSet.initOne(.amdgpu) } },
5617 // __builtin_amdgcn_sched_group_barrier
5618 .{ .tag = @enumFromInt(223), .properties = .{ .param_str = "vIiIiIi", .target_set = TargetSet.initOne(.amdgpu) } },
5619 // __builtin_amdgcn_sicmp
5620 .{ .tag = @enumFromInt(224), .properties = .{ .param_str = "WUiiiIi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5621 // __builtin_amdgcn_sicmpl
5622 .{ .tag = @enumFromInt(225), .properties = .{ .param_str = "WUiWiWiIi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5623 // __builtin_amdgcn_sinf
5624 .{ .tag = @enumFromInt(226), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5625 // __builtin_amdgcn_sqrt
5626 .{ .tag = @enumFromInt(227), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5627 // __builtin_amdgcn_sqrtf
5628 .{ .tag = @enumFromInt(228), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5629 // __builtin_amdgcn_trig_preop
5630 .{ .tag = @enumFromInt(229), .properties = .{ .param_str = "ddi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5631 // __builtin_amdgcn_trig_preopf
5632 .{ .tag = @enumFromInt(230), .properties = .{ .param_str = "ffi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5633 // __builtin_amdgcn_ubfe
5634 .{ .tag = @enumFromInt(231), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5635 // __builtin_amdgcn_uicmp
5636 .{ .tag = @enumFromInt(232), .properties = .{ .param_str = "WUiUiUiIi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5637 // __builtin_amdgcn_uicmpl
5638 .{ .tag = @enumFromInt(233), .properties = .{ .param_str = "WUiWUiWUiIi", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5639 // __builtin_amdgcn_wave_barrier
5640 .{ .tag = @enumFromInt(234), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.amdgpu) } },
5641 // __builtin_amdgcn_workgroup_id_x
5642 .{ .tag = @enumFromInt(235), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5643 // __builtin_amdgcn_workgroup_id_y
5644 .{ .tag = @enumFromInt(236), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5645 // __builtin_amdgcn_workgroup_id_z
5646 .{ .tag = @enumFromInt(237), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5647 // __builtin_amdgcn_workgroup_size_x
5648 .{ .tag = @enumFromInt(238), .properties = .{ .param_str = "Us", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5649 // __builtin_amdgcn_workgroup_size_y
5650 .{ .tag = @enumFromInt(239), .properties = .{ .param_str = "Us", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5651 // __builtin_amdgcn_workgroup_size_z
5652 .{ .tag = @enumFromInt(240), .properties = .{ .param_str = "Us", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5653 // __builtin_amdgcn_workitem_id_x
5654 .{ .tag = @enumFromInt(241), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5655 // __builtin_amdgcn_workitem_id_y
5656 .{ .tag = @enumFromInt(242), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5657 // __builtin_amdgcn_workitem_id_z
5658 .{ .tag = @enumFromInt(243), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
5659 // __builtin_annotation
5660 .{ .tag = @enumFromInt(244), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
5661 // __builtin_arm_cdp
5662 .{ .tag = @enumFromInt(245), .properties = .{ .param_str = "vUIiUIiUIiUIiUIiUIi", .target_set = TargetSet.initOne(.arm) } },
5663 // __builtin_arm_cdp2
5664 .{ .tag = @enumFromInt(246), .properties = .{ .param_str = "vUIiUIiUIiUIiUIiUIi", .target_set = TargetSet.initOne(.arm) } },
5665 // __builtin_arm_clrex
5666 .{ .tag = @enumFromInt(247), .properties = .{ .param_str = "v", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
5667 // __builtin_arm_cls
5668 .{ .tag = @enumFromInt(248), .properties = .{ .param_str = "UiZUi", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5669 // __builtin_arm_cls64
5670 .{ .tag = @enumFromInt(249), .properties = .{ .param_str = "UiWUi", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5671 // __builtin_arm_clz
5672 .{ .tag = @enumFromInt(250), .properties = .{ .param_str = "UiZUi", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5673 // __builtin_arm_clz64
5674 .{ .tag = @enumFromInt(251), .properties = .{ .param_str = "UiWUi", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5675 // __builtin_arm_cmse_TT
5676 .{ .tag = @enumFromInt(252), .properties = .{ .param_str = "Uiv*", .target_set = TargetSet.initOne(.arm) } },
5677 // __builtin_arm_cmse_TTA
5678 .{ .tag = @enumFromInt(253), .properties = .{ .param_str = "Uiv*", .target_set = TargetSet.initOne(.arm) } },
5679 // __builtin_arm_cmse_TTAT
5680 .{ .tag = @enumFromInt(254), .properties = .{ .param_str = "Uiv*", .target_set = TargetSet.initOne(.arm) } },
5681 // __builtin_arm_cmse_TTT
5682 .{ .tag = @enumFromInt(255), .properties = .{ .param_str = "Uiv*", .target_set = TargetSet.initOne(.arm) } },
5683 // __builtin_arm_dbg
5684 .{ .tag = @enumFromInt(256), .properties = .{ .param_str = "vUi", .target_set = TargetSet.initOne(.arm) } },
5685 // __builtin_arm_dmb
5686 .{ .tag = @enumFromInt(257), .properties = .{ .param_str = "vUi", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5687 // __builtin_arm_dsb
5688 .{ .tag = @enumFromInt(258), .properties = .{ .param_str = "vUi", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5689 // __builtin_arm_get_fpscr
5690 .{ .tag = @enumFromInt(259), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5691 // __builtin_arm_isb
5692 .{ .tag = @enumFromInt(260), .properties = .{ .param_str = "vUi", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5693 // __builtin_arm_ldaex
5694 .{ .tag = @enumFromInt(261), .properties = .{ .param_str = "v.", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .custom_typecheck = true } } },
5695 // __builtin_arm_ldc
5696 .{ .tag = @enumFromInt(262), .properties = .{ .param_str = "vUIiUIivC*", .target_set = TargetSet.initOne(.arm) } },
5697 // __builtin_arm_ldc2
5698 .{ .tag = @enumFromInt(263), .properties = .{ .param_str = "vUIiUIivC*", .target_set = TargetSet.initOne(.arm) } },
5699 // __builtin_arm_ldc2l
5700 .{ .tag = @enumFromInt(264), .properties = .{ .param_str = "vUIiUIivC*", .target_set = TargetSet.initOne(.arm) } },
5701 // __builtin_arm_ldcl
5702 .{ .tag = @enumFromInt(265), .properties = .{ .param_str = "vUIiUIivC*", .target_set = TargetSet.initOne(.arm) } },
5703 // __builtin_arm_ldrex
5704 .{ .tag = @enumFromInt(266), .properties = .{ .param_str = "v.", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .custom_typecheck = true } } },
5705 // __builtin_arm_ldrexd
5706 .{ .tag = @enumFromInt(267), .properties = .{ .param_str = "LLUiv*", .target_set = TargetSet.initOne(.arm) } },
5707 // __builtin_arm_mcr
5708 .{ .tag = @enumFromInt(268), .properties = .{ .param_str = "vUIiUIiUiUIiUIiUIi", .target_set = TargetSet.initOne(.arm) } },
5709 // __builtin_arm_mcr2
5710 .{ .tag = @enumFromInt(269), .properties = .{ .param_str = "vUIiUIiUiUIiUIiUIi", .target_set = TargetSet.initOne(.arm) } },
5711 // __builtin_arm_mcrr
5712 .{ .tag = @enumFromInt(270), .properties = .{ .param_str = "vUIiUIiLLUiUIi", .target_set = TargetSet.initOne(.arm) } },
5713 // __builtin_arm_mcrr2
5714 .{ .tag = @enumFromInt(271), .properties = .{ .param_str = "vUIiUIiLLUiUIi", .target_set = TargetSet.initOne(.arm) } },
5715 // __builtin_arm_mrc
5716 .{ .tag = @enumFromInt(272), .properties = .{ .param_str = "UiUIiUIiUIiUIiUIi", .target_set = TargetSet.initOne(.arm) } },
5717 // __builtin_arm_mrc2
5718 .{ .tag = @enumFromInt(273), .properties = .{ .param_str = "UiUIiUIiUIiUIiUIi", .target_set = TargetSet.initOne(.arm) } },
5719 // __builtin_arm_mrrc
5720 .{ .tag = @enumFromInt(274), .properties = .{ .param_str = "LLUiUIiUIiUIi", .target_set = TargetSet.initOne(.arm) } },
5721 // __builtin_arm_mrrc2
5722 .{ .tag = @enumFromInt(275), .properties = .{ .param_str = "LLUiUIiUIiUIi", .target_set = TargetSet.initOne(.arm) } },
5723 // __builtin_arm_nop
5724 .{ .tag = @enumFromInt(276), .properties = .{ .param_str = "v", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
5725 // __builtin_arm_prefetch
5726 .{ .tag = @enumFromInt(277), .properties = .{ .param_str = "!", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5727 // __builtin_arm_qadd
5728 .{ .tag = @enumFromInt(278), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5729 // __builtin_arm_qadd16
5730 .{ .tag = @enumFromInt(279), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5731 // __builtin_arm_qadd8
5732 .{ .tag = @enumFromInt(280), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5733 // __builtin_arm_qasx
5734 .{ .tag = @enumFromInt(281), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5735 // __builtin_arm_qdbl
5736 .{ .tag = @enumFromInt(282), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5737 // __builtin_arm_qsax
5738 .{ .tag = @enumFromInt(283), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5739 // __builtin_arm_qsub
5740 .{ .tag = @enumFromInt(284), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5741 // __builtin_arm_qsub16
5742 .{ .tag = @enumFromInt(285), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5743 // __builtin_arm_qsub8
5744 .{ .tag = @enumFromInt(286), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5745 // __builtin_arm_rbit
5746 .{ .tag = @enumFromInt(287), .properties = .{ .param_str = "UiUi", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5747 // __builtin_arm_rbit64
5748 .{ .tag = @enumFromInt(288), .properties = .{ .param_str = "WUiWUi", .target_set = TargetSet.initOne(.aarch64), .attributes = .{ .@"const" = true } } },
5749 // __builtin_arm_rsr
5750 .{ .tag = @enumFromInt(289), .properties = .{ .param_str = "UicC*", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5751 // __builtin_arm_rsr64
5752 .{ .tag = @enumFromInt(290), .properties = .{ .param_str = "!", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5753 // __builtin_arm_rsrp
5754 .{ .tag = @enumFromInt(291), .properties = .{ .param_str = "v*cC*", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5755 // __builtin_arm_sadd16
5756 .{ .tag = @enumFromInt(292), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5757 // __builtin_arm_sadd8
5758 .{ .tag = @enumFromInt(293), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5759 // __builtin_arm_sasx
5760 .{ .tag = @enumFromInt(294), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5761 // __builtin_arm_sel
5762 .{ .tag = @enumFromInt(295), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5763 // __builtin_arm_set_fpscr
5764 .{ .tag = @enumFromInt(296), .properties = .{ .param_str = "vUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5765 // __builtin_arm_sev
5766 .{ .tag = @enumFromInt(297), .properties = .{ .param_str = "v", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
5767 // __builtin_arm_sevl
5768 .{ .tag = @enumFromInt(298), .properties = .{ .param_str = "v", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
5769 // __builtin_arm_shadd16
5770 .{ .tag = @enumFromInt(299), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5771 // __builtin_arm_shadd8
5772 .{ .tag = @enumFromInt(300), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5773 // __builtin_arm_shasx
5774 .{ .tag = @enumFromInt(301), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5775 // __builtin_arm_shsax
5776 .{ .tag = @enumFromInt(302), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5777 // __builtin_arm_shsub16
5778 .{ .tag = @enumFromInt(303), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5779 // __builtin_arm_shsub8
5780 .{ .tag = @enumFromInt(304), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5781 // __builtin_arm_smlabb
5782 .{ .tag = @enumFromInt(305), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5783 // __builtin_arm_smlabt
5784 .{ .tag = @enumFromInt(306), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5785 // __builtin_arm_smlad
5786 .{ .tag = @enumFromInt(307), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5787 // __builtin_arm_smladx
5788 .{ .tag = @enumFromInt(308), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5789 // __builtin_arm_smlald
5790 .{ .tag = @enumFromInt(309), .properties = .{ .param_str = "LLiiiLLi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5791 // __builtin_arm_smlaldx
5792 .{ .tag = @enumFromInt(310), .properties = .{ .param_str = "LLiiiLLi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5793 // __builtin_arm_smlatb
5794 .{ .tag = @enumFromInt(311), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5795 // __builtin_arm_smlatt
5796 .{ .tag = @enumFromInt(312), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5797 // __builtin_arm_smlawb
5798 .{ .tag = @enumFromInt(313), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5799 // __builtin_arm_smlawt
5800 .{ .tag = @enumFromInt(314), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5801 // __builtin_arm_smlsd
5802 .{ .tag = @enumFromInt(315), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5803 // __builtin_arm_smlsdx
5804 .{ .tag = @enumFromInt(316), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5805 // __builtin_arm_smlsld
5806 .{ .tag = @enumFromInt(317), .properties = .{ .param_str = "LLiiiLLi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5807 // __builtin_arm_smlsldx
5808 .{ .tag = @enumFromInt(318), .properties = .{ .param_str = "LLiiiLLi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5809 // __builtin_arm_smuad
5810 .{ .tag = @enumFromInt(319), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5811 // __builtin_arm_smuadx
5812 .{ .tag = @enumFromInt(320), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5813 // __builtin_arm_smulbb
5814 .{ .tag = @enumFromInt(321), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5815 // __builtin_arm_smulbt
5816 .{ .tag = @enumFromInt(322), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5817 // __builtin_arm_smultb
5818 .{ .tag = @enumFromInt(323), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5819 // __builtin_arm_smultt
5820 .{ .tag = @enumFromInt(324), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5821 // __builtin_arm_smulwb
5822 .{ .tag = @enumFromInt(325), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5823 // __builtin_arm_smulwt
5824 .{ .tag = @enumFromInt(326), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5825 // __builtin_arm_smusd
5826 .{ .tag = @enumFromInt(327), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5827 // __builtin_arm_smusdx
5828 .{ .tag = @enumFromInt(328), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5829 // __builtin_arm_ssat
5830 .{ .tag = @enumFromInt(329), .properties = .{ .param_str = "iiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5831 // __builtin_arm_ssat16
5832 .{ .tag = @enumFromInt(330), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5833 // __builtin_arm_ssax
5834 .{ .tag = @enumFromInt(331), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5835 // __builtin_arm_ssub16
5836 .{ .tag = @enumFromInt(332), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5837 // __builtin_arm_ssub8
5838 .{ .tag = @enumFromInt(333), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5839 // __builtin_arm_stc
5840 .{ .tag = @enumFromInt(334), .properties = .{ .param_str = "vUIiUIiv*", .target_set = TargetSet.initOne(.arm) } },
5841 // __builtin_arm_stc2
5842 .{ .tag = @enumFromInt(335), .properties = .{ .param_str = "vUIiUIiv*", .target_set = TargetSet.initOne(.arm) } },
5843 // __builtin_arm_stc2l
5844 .{ .tag = @enumFromInt(336), .properties = .{ .param_str = "vUIiUIiv*", .target_set = TargetSet.initOne(.arm) } },
5845 // __builtin_arm_stcl
5846 .{ .tag = @enumFromInt(337), .properties = .{ .param_str = "vUIiUIiv*", .target_set = TargetSet.initOne(.arm) } },
5847 // __builtin_arm_stlex
5848 .{ .tag = @enumFromInt(338), .properties = .{ .param_str = "i.", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .custom_typecheck = true } } },
5849 // __builtin_arm_strex
5850 .{ .tag = @enumFromInt(339), .properties = .{ .param_str = "i.", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .custom_typecheck = true } } },
5851 // __builtin_arm_strexd
5852 .{ .tag = @enumFromInt(340), .properties = .{ .param_str = "iLLUiv*", .target_set = TargetSet.initOne(.arm) } },
5853 // __builtin_arm_sxtab16
5854 .{ .tag = @enumFromInt(341), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5855 // __builtin_arm_sxtb16
5856 .{ .tag = @enumFromInt(342), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5857 // __builtin_arm_tcancel
5858 .{ .tag = @enumFromInt(343), .properties = .{ .param_str = "vWUIi", .target_set = TargetSet.initOne(.aarch64) } },
5859 // __builtin_arm_tcommit
5860 .{ .tag = @enumFromInt(344), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.aarch64) } },
5861 // __builtin_arm_tstart
5862 .{ .tag = @enumFromInt(345), .properties = .{ .param_str = "WUi", .target_set = TargetSet.initOne(.aarch64), .attributes = .{ .returns_twice = true } } },
5863 // __builtin_arm_ttest
5864 .{ .tag = @enumFromInt(346), .properties = .{ .param_str = "WUi", .target_set = TargetSet.initOne(.aarch64), .attributes = .{ .@"const" = true } } },
5865 // __builtin_arm_uadd16
5866 .{ .tag = @enumFromInt(347), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5867 // __builtin_arm_uadd8
5868 .{ .tag = @enumFromInt(348), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5869 // __builtin_arm_uasx
5870 .{ .tag = @enumFromInt(349), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5871 // __builtin_arm_uhadd16
5872 .{ .tag = @enumFromInt(350), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5873 // __builtin_arm_uhadd8
5874 .{ .tag = @enumFromInt(351), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5875 // __builtin_arm_uhasx
5876 .{ .tag = @enumFromInt(352), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5877 // __builtin_arm_uhsax
5878 .{ .tag = @enumFromInt(353), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5879 // __builtin_arm_uhsub16
5880 .{ .tag = @enumFromInt(354), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5881 // __builtin_arm_uhsub8
5882 .{ .tag = @enumFromInt(355), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5883 // __builtin_arm_uqadd16
5884 .{ .tag = @enumFromInt(356), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5885 // __builtin_arm_uqadd8
5886 .{ .tag = @enumFromInt(357), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5887 // __builtin_arm_uqasx
5888 .{ .tag = @enumFromInt(358), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5889 // __builtin_arm_uqsax
5890 .{ .tag = @enumFromInt(359), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5891 // __builtin_arm_uqsub16
5892 .{ .tag = @enumFromInt(360), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5893 // __builtin_arm_uqsub8
5894 .{ .tag = @enumFromInt(361), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5895 // __builtin_arm_usad8
5896 .{ .tag = @enumFromInt(362), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5897 // __builtin_arm_usada8
5898 .{ .tag = @enumFromInt(363), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5899 // __builtin_arm_usat
5900 .{ .tag = @enumFromInt(364), .properties = .{ .param_str = "UiiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5901 // __builtin_arm_usat16
5902 .{ .tag = @enumFromInt(365), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5903 // __builtin_arm_usax
5904 .{ .tag = @enumFromInt(366), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5905 // __builtin_arm_usub16
5906 .{ .tag = @enumFromInt(367), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5907 // __builtin_arm_usub8
5908 .{ .tag = @enumFromInt(368), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5909 // __builtin_arm_uxtab16
5910 .{ .tag = @enumFromInt(369), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5911 // __builtin_arm_uxtb16
5912 .{ .tag = @enumFromInt(370), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5913 // __builtin_arm_vcvtr_d
5914 .{ .tag = @enumFromInt(371), .properties = .{ .param_str = "fdi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5915 // __builtin_arm_vcvtr_f
5916 .{ .tag = @enumFromInt(372), .properties = .{ .param_str = "ffi", .target_set = TargetSet.initOne(.arm), .attributes = .{ .@"const" = true } } },
5917 // __builtin_arm_wfe
5918 .{ .tag = @enumFromInt(373), .properties = .{ .param_str = "v", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
5919 // __builtin_arm_wfi
5920 .{ .tag = @enumFromInt(374), .properties = .{ .param_str = "v", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
5921 // __builtin_arm_wsr
5922 .{ .tag = @enumFromInt(375), .properties = .{ .param_str = "vcC*Ui", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5923 // __builtin_arm_wsr64
5924 .{ .tag = @enumFromInt(376), .properties = .{ .param_str = "!", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5925 // __builtin_arm_wsrp
5926 .{ .tag = @enumFromInt(377), .properties = .{ .param_str = "vcC*vC*", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
5927 // __builtin_arm_yield
5928 .{ .tag = @enumFromInt(378), .properties = .{ .param_str = "v", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
5929 // __builtin_asin
5930 .{ .tag = @enumFromInt(379), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5931 // __builtin_asinf
5932 .{ .tag = @enumFromInt(380), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5933 // __builtin_asinf128
5934 .{ .tag = @enumFromInt(381), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5935 // __builtin_asinh
5936 .{ .tag = @enumFromInt(382), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5937 // __builtin_asinhf
5938 .{ .tag = @enumFromInt(383), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5939 // __builtin_asinhf128
5940 .{ .tag = @enumFromInt(384), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5941 // __builtin_asinhl
5942 .{ .tag = @enumFromInt(385), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5943 // __builtin_asinl
5944 .{ .tag = @enumFromInt(386), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5945 // __builtin_assume
5946 .{ .tag = @enumFromInt(387), .properties = .{ .param_str = "vb", .attributes = .{ .const_evaluable = true } } },
5947 // __builtin_assume_aligned
5948 .{ .tag = @enumFromInt(388), .properties = .{ .param_str = "v*vC*z.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .const_evaluable = true } } },
5949 // __builtin_assume_separate_storage
5950 .{ .tag = @enumFromInt(389), .properties = .{ .param_str = "vvCD*vCD*", .attributes = .{ .const_evaluable = true } } },
5951 // __builtin_atan
5952 .{ .tag = @enumFromInt(390), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5953 // __builtin_atan2
5954 .{ .tag = @enumFromInt(391), .properties = .{ .param_str = "ddd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5955 // __builtin_atan2f
5956 .{ .tag = @enumFromInt(392), .properties = .{ .param_str = "fff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5957 // __builtin_atan2f128
5958 .{ .tag = @enumFromInt(393), .properties = .{ .param_str = "LLdLLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5959 // __builtin_atan2l
5960 .{ .tag = @enumFromInt(394), .properties = .{ .param_str = "LdLdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5961 // __builtin_atanf
5962 .{ .tag = @enumFromInt(395), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5963 // __builtin_atanf128
5964 .{ .tag = @enumFromInt(396), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5965 // __builtin_atanh
5966 .{ .tag = @enumFromInt(397), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5967 // __builtin_atanhf
5968 .{ .tag = @enumFromInt(398), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5969 // __builtin_atanhf128
5970 .{ .tag = @enumFromInt(399), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5971 // __builtin_atanhl
5972 .{ .tag = @enumFromInt(400), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5973 // __builtin_atanl
5974 .{ .tag = @enumFromInt(401), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5975 // __builtin_bcmp
5976 .{ .tag = @enumFromInt(402), .properties = .{ .param_str = "ivC*vC*z", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
5977 // __builtin_bcopy
5978 .{ .tag = @enumFromInt(403), .properties = .{ .param_str = "vvC*v*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5979 // __builtin_bitrev
5980 .{ .tag = @enumFromInt(404), .properties = .{ .param_str = "UiUi", .target_set = TargetSet.initOne(.xcore), .attributes = .{ .@"const" = true } } },
5981 // __builtin_bitreverse16
5982 .{ .tag = @enumFromInt(405), .properties = .{ .param_str = "UsUs", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
5983 // __builtin_bitreverse32
5984 .{ .tag = @enumFromInt(406), .properties = .{ .param_str = "UZiUZi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
5985 // __builtin_bitreverse64
5986 .{ .tag = @enumFromInt(407), .properties = .{ .param_str = "UWiUWi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
5987 // __builtin_bitreverse8
5988 .{ .tag = @enumFromInt(408), .properties = .{ .param_str = "UcUc", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
5989 // __builtin_bswap16
5990 .{ .tag = @enumFromInt(409), .properties = .{ .param_str = "UsUs", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
5991 // __builtin_bswap32
5992 .{ .tag = @enumFromInt(410), .properties = .{ .param_str = "UZiUZi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
5993 // __builtin_bswap64
5994 .{ .tag = @enumFromInt(411), .properties = .{ .param_str = "UWiUWi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
5995 // __builtin_bzero
5996 .{ .tag = @enumFromInt(412), .properties = .{ .param_str = "vv*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
5997 // __builtin_cabs
5998 .{ .tag = @enumFromInt(413), .properties = .{ .param_str = "dXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
5999 // __builtin_cabsf
6000 .{ .tag = @enumFromInt(414), .properties = .{ .param_str = "fXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6001 // __builtin_cabsl
6002 .{ .tag = @enumFromInt(415), .properties = .{ .param_str = "LdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6003 // __builtin_cacos
6004 .{ .tag = @enumFromInt(416), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6005 // __builtin_cacosf
6006 .{ .tag = @enumFromInt(417), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6007 // __builtin_cacosh
6008 .{ .tag = @enumFromInt(418), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6009 // __builtin_cacoshf
6010 .{ .tag = @enumFromInt(419), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6011 // __builtin_cacoshl
6012 .{ .tag = @enumFromInt(420), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6013 // __builtin_cacosl
6014 .{ .tag = @enumFromInt(421), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6015 // __builtin_call_with_static_chain
6016 .{ .tag = @enumFromInt(422), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
6017 // __builtin_calloc
6018 .{ .tag = @enumFromInt(423), .properties = .{ .param_str = "v*zz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6019 // __builtin_canonicalize
6020 .{ .tag = @enumFromInt(424), .properties = .{ .param_str = "dd", .attributes = .{ .@"const" = true } } },
6021 // __builtin_canonicalizef
6022 .{ .tag = @enumFromInt(425), .properties = .{ .param_str = "ff", .attributes = .{ .@"const" = true } } },
6023 // __builtin_canonicalizef16
6024 .{ .tag = @enumFromInt(426), .properties = .{ .param_str = "hh", .attributes = .{ .@"const" = true } } },
6025 // __builtin_canonicalizel
6026 .{ .tag = @enumFromInt(427), .properties = .{ .param_str = "LdLd", .attributes = .{ .@"const" = true } } },
6027 // __builtin_carg
6028 .{ .tag = @enumFromInt(428), .properties = .{ .param_str = "dXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6029 // __builtin_cargf
6030 .{ .tag = @enumFromInt(429), .properties = .{ .param_str = "fXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6031 // __builtin_cargl
6032 .{ .tag = @enumFromInt(430), .properties = .{ .param_str = "LdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6033 // __builtin_casin
6034 .{ .tag = @enumFromInt(431), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6035 // __builtin_casinf
6036 .{ .tag = @enumFromInt(432), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6037 // __builtin_casinh
6038 .{ .tag = @enumFromInt(433), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6039 // __builtin_casinhf
6040 .{ .tag = @enumFromInt(434), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6041 // __builtin_casinhl
6042 .{ .tag = @enumFromInt(435), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6043 // __builtin_casinl
6044 .{ .tag = @enumFromInt(436), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6045 // __builtin_catan
6046 .{ .tag = @enumFromInt(437), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6047 // __builtin_catanf
6048 .{ .tag = @enumFromInt(438), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6049 // __builtin_catanh
6050 .{ .tag = @enumFromInt(439), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6051 // __builtin_catanhf
6052 .{ .tag = @enumFromInt(440), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6053 // __builtin_catanhl
6054 .{ .tag = @enumFromInt(441), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6055 // __builtin_catanl
6056 .{ .tag = @enumFromInt(442), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6057 // __builtin_cbrt
6058 .{ .tag = @enumFromInt(443), .properties = .{ .param_str = "dd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6059 // __builtin_cbrtf
6060 .{ .tag = @enumFromInt(444), .properties = .{ .param_str = "ff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6061 // __builtin_cbrtf128
6062 .{ .tag = @enumFromInt(445), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6063 // __builtin_cbrtl
6064 .{ .tag = @enumFromInt(446), .properties = .{ .param_str = "LdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6065 // __builtin_ccos
6066 .{ .tag = @enumFromInt(447), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6067 // __builtin_ccosf
6068 .{ .tag = @enumFromInt(448), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6069 // __builtin_ccosh
6070 .{ .tag = @enumFromInt(449), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6071 // __builtin_ccoshf
6072 .{ .tag = @enumFromInt(450), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6073 // __builtin_ccoshl
6074 .{ .tag = @enumFromInt(451), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6075 // __builtin_ccosl
6076 .{ .tag = @enumFromInt(452), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6077 // __builtin_ceil
6078 .{ .tag = @enumFromInt(453), .properties = .{ .param_str = "dd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6079 // __builtin_ceilf
6080 .{ .tag = @enumFromInt(454), .properties = .{ .param_str = "ff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6081 // __builtin_ceilf128
6082 .{ .tag = @enumFromInt(455), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6083 // __builtin_ceilf16
6084 .{ .tag = @enumFromInt(456), .properties = .{ .param_str = "hh", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6085 // __builtin_ceill
6086 .{ .tag = @enumFromInt(457), .properties = .{ .param_str = "LdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6087 // __builtin_cexp
6088 .{ .tag = @enumFromInt(458), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6089 // __builtin_cexpf
6090 .{ .tag = @enumFromInt(459), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6091 // __builtin_cexpl
6092 .{ .tag = @enumFromInt(460), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6093 // __builtin_char_memchr
6094 .{ .tag = @enumFromInt(461), .properties = .{ .param_str = "c*cC*iz", .attributes = .{ .const_evaluable = true } } },
6095 // __builtin_cimag
6096 .{ .tag = @enumFromInt(462), .properties = .{ .param_str = "dXd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6097 // __builtin_cimagf
6098 .{ .tag = @enumFromInt(463), .properties = .{ .param_str = "fXf", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6099 // __builtin_cimagl
6100 .{ .tag = @enumFromInt(464), .properties = .{ .param_str = "LdXLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6101 // __builtin_classify_type
6102 .{ .tag = @enumFromInt(465), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .eval_args = false, .const_evaluable = true } } },
6103 // __builtin_clog
6104 .{ .tag = @enumFromInt(466), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6105 // __builtin_clogf
6106 .{ .tag = @enumFromInt(467), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6107 // __builtin_clogl
6108 .{ .tag = @enumFromInt(468), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6109 // __builtin_clrsb
6110 .{ .tag = @enumFromInt(469), .properties = .{ .param_str = "ii", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6111 // __builtin_clrsbl
6112 .{ .tag = @enumFromInt(470), .properties = .{ .param_str = "iLi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6113 // __builtin_clrsbll
6114 .{ .tag = @enumFromInt(471), .properties = .{ .param_str = "iLLi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6115 // __builtin_clz
6116 .{ .tag = @enumFromInt(472), .properties = .{ .param_str = "iUi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6117 // __builtin_clzl
6118 .{ .tag = @enumFromInt(473), .properties = .{ .param_str = "iULi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6119 // __builtin_clzll
6120 .{ .tag = @enumFromInt(474), .properties = .{ .param_str = "iULLi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6121 // __builtin_clzs
6122 .{ .tag = @enumFromInt(475), .properties = .{ .param_str = "iUs", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6123 // __builtin_complex
6124 .{ .tag = @enumFromInt(476), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .const_evaluable = true } } },
6125 // __builtin_conj
6126 .{ .tag = @enumFromInt(477), .properties = .{ .param_str = "XdXd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6127 // __builtin_conjf
6128 .{ .tag = @enumFromInt(478), .properties = .{ .param_str = "XfXf", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6129 // __builtin_conjl
6130 .{ .tag = @enumFromInt(479), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6131 // __builtin_constant_p
6132 .{ .tag = @enumFromInt(480), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .eval_args = false, .const_evaluable = true } } },
6133 // __builtin_convertvector
6134 .{ .tag = @enumFromInt(481), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6135 // __builtin_copysign
6136 .{ .tag = @enumFromInt(482), .properties = .{ .param_str = "ddd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6137 // __builtin_copysignf
6138 .{ .tag = @enumFromInt(483), .properties = .{ .param_str = "fff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6139 // __builtin_copysignf128
6140 .{ .tag = @enumFromInt(484), .properties = .{ .param_str = "LLdLLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6141 // __builtin_copysignf16
6142 .{ .tag = @enumFromInt(485), .properties = .{ .param_str = "hhh", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6143 // __builtin_copysignl
6144 .{ .tag = @enumFromInt(486), .properties = .{ .param_str = "LdLdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6145 // __builtin_cos
6146 .{ .tag = @enumFromInt(487), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6147 // __builtin_cosf
6148 .{ .tag = @enumFromInt(488), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6149 // __builtin_cosf128
6150 .{ .tag = @enumFromInt(489), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6151 // __builtin_cosf16
6152 .{ .tag = @enumFromInt(490), .properties = .{ .param_str = "hh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6153 // __builtin_cosh
6154 .{ .tag = @enumFromInt(491), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6155 // __builtin_coshf
6156 .{ .tag = @enumFromInt(492), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6157 // __builtin_coshf128
6158 .{ .tag = @enumFromInt(493), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6159 // __builtin_coshl
6160 .{ .tag = @enumFromInt(494), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6161 // __builtin_cosl
6162 .{ .tag = @enumFromInt(495), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6163 // __builtin_cpow
6164 .{ .tag = @enumFromInt(496), .properties = .{ .param_str = "XdXdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6165 // __builtin_cpowf
6166 .{ .tag = @enumFromInt(497), .properties = .{ .param_str = "XfXfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6167 // __builtin_cpowl
6168 .{ .tag = @enumFromInt(498), .properties = .{ .param_str = "XLdXLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6169 // __builtin_cproj
6170 .{ .tag = @enumFromInt(499), .properties = .{ .param_str = "XdXd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6171 // __builtin_cprojf
6172 .{ .tag = @enumFromInt(500), .properties = .{ .param_str = "XfXf", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6173 // __builtin_cprojl
6174 .{ .tag = @enumFromInt(501), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6175 // __builtin_cpu_init
6176 .{ .tag = @enumFromInt(502), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.x86) } },
6177 // __builtin_cpu_is
6178 .{ .tag = @enumFromInt(503), .properties = .{ .param_str = "bcC*", .target_set = TargetSet.initOne(.x86), .attributes = .{ .@"const" = true } } },
6179 // __builtin_cpu_supports
6180 .{ .tag = @enumFromInt(504), .properties = .{ .param_str = "bcC*", .target_set = TargetSet.initOne(.x86), .attributes = .{ .@"const" = true } } },
6181 // __builtin_creal
6182 .{ .tag = @enumFromInt(505), .properties = .{ .param_str = "dXd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6183 // __builtin_crealf
6184 .{ .tag = @enumFromInt(506), .properties = .{ .param_str = "fXf", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6185 // __builtin_creall
6186 .{ .tag = @enumFromInt(507), .properties = .{ .param_str = "LdXLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6187 // __builtin_csin
6188 .{ .tag = @enumFromInt(508), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6189 // __builtin_csinf
6190 .{ .tag = @enumFromInt(509), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6191 // __builtin_csinh
6192 .{ .tag = @enumFromInt(510), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6193 // __builtin_csinhf
6194 .{ .tag = @enumFromInt(511), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6195 // __builtin_csinhl
6196 .{ .tag = @enumFromInt(512), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6197 // __builtin_csinl
6198 .{ .tag = @enumFromInt(513), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6199 // __builtin_csqrt
6200 .{ .tag = @enumFromInt(514), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6201 // __builtin_csqrtf
6202 .{ .tag = @enumFromInt(515), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6203 // __builtin_csqrtl
6204 .{ .tag = @enumFromInt(516), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6205 // __builtin_ctan
6206 .{ .tag = @enumFromInt(517), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6207 // __builtin_ctanf
6208 .{ .tag = @enumFromInt(518), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6209 // __builtin_ctanh
6210 .{ .tag = @enumFromInt(519), .properties = .{ .param_str = "XdXd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6211 // __builtin_ctanhf
6212 .{ .tag = @enumFromInt(520), .properties = .{ .param_str = "XfXf", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6213 // __builtin_ctanhl
6214 .{ .tag = @enumFromInt(521), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6215 // __builtin_ctanl
6216 .{ .tag = @enumFromInt(522), .properties = .{ .param_str = "XLdXLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6217 // __builtin_ctz
6218 .{ .tag = @enumFromInt(523), .properties = .{ .param_str = "iUi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6219 // __builtin_ctzl
6220 .{ .tag = @enumFromInt(524), .properties = .{ .param_str = "iULi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6221 // __builtin_ctzll
6222 .{ .tag = @enumFromInt(525), .properties = .{ .param_str = "iULLi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6223 // __builtin_ctzs
6224 .{ .tag = @enumFromInt(526), .properties = .{ .param_str = "iUs", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6225 // __builtin_dcbf
6226 .{ .tag = @enumFromInt(527), .properties = .{ .param_str = "vvC*", .target_set = TargetSet.initOne(.ppc) } },
6227 // __builtin_debugtrap
6228 .{ .tag = @enumFromInt(528), .properties = .{ .param_str = "v" } },
6229 // __builtin_dump_struct
6230 .{ .tag = @enumFromInt(529), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
6231 // __builtin_dwarf_cfa
6232 .{ .tag = @enumFromInt(530), .properties = .{ .param_str = "v*" } },
6233 // __builtin_dwarf_sp_column
6234 .{ .tag = @enumFromInt(531), .properties = .{ .param_str = "Ui" } },
6235 // __builtin_dynamic_object_size
6236 .{ .tag = @enumFromInt(532), .properties = .{ .param_str = "zvC*i", .attributes = .{ .eval_args = false, .const_evaluable = true } } },
6237 // __builtin_eh_return
6238 .{ .tag = @enumFromInt(533), .properties = .{ .param_str = "vzv*", .attributes = .{ .noreturn = true } } },
6239 // __builtin_eh_return_data_regno
6240 .{ .tag = @enumFromInt(534), .properties = .{ .param_str = "iIi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6241 // __builtin_elementwise_abs
6242 .{ .tag = @enumFromInt(535), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6243 // __builtin_elementwise_add_sat
6244 .{ .tag = @enumFromInt(536), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6245 // __builtin_elementwise_bitreverse
6246 .{ .tag = @enumFromInt(537), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6247 // __builtin_elementwise_canonicalize
6248 .{ .tag = @enumFromInt(538), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6249 // __builtin_elementwise_ceil
6250 .{ .tag = @enumFromInt(539), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6251 // __builtin_elementwise_copysign
6252 .{ .tag = @enumFromInt(540), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6253 // __builtin_elementwise_cos
6254 .{ .tag = @enumFromInt(541), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6255 // __builtin_elementwise_exp
6256 .{ .tag = @enumFromInt(542), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6257 // __builtin_elementwise_exp2
6258 .{ .tag = @enumFromInt(543), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6259 // __builtin_elementwise_floor
6260 .{ .tag = @enumFromInt(544), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6261 // __builtin_elementwise_fma
6262 .{ .tag = @enumFromInt(545), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6263 // __builtin_elementwise_log
6264 .{ .tag = @enumFromInt(546), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6265 // __builtin_elementwise_log10
6266 .{ .tag = @enumFromInt(547), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6267 // __builtin_elementwise_log2
6268 .{ .tag = @enumFromInt(548), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6269 // __builtin_elementwise_max
6270 .{ .tag = @enumFromInt(549), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6271 // __builtin_elementwise_min
6272 .{ .tag = @enumFromInt(550), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6273 // __builtin_elementwise_nearbyint
6274 .{ .tag = @enumFromInt(551), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6275 // __builtin_elementwise_pow
6276 .{ .tag = @enumFromInt(552), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6277 // __builtin_elementwise_rint
6278 .{ .tag = @enumFromInt(553), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6279 // __builtin_elementwise_round
6280 .{ .tag = @enumFromInt(554), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6281 // __builtin_elementwise_roundeven
6282 .{ .tag = @enumFromInt(555), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6283 // __builtin_elementwise_sin
6284 .{ .tag = @enumFromInt(556), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6285 // __builtin_elementwise_sqrt
6286 .{ .tag = @enumFromInt(557), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6287 // __builtin_elementwise_sub_sat
6288 .{ .tag = @enumFromInt(558), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6289 // __builtin_elementwise_trunc
6290 .{ .tag = @enumFromInt(559), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
6291 // __builtin_erf
6292 .{ .tag = @enumFromInt(560), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6293 // __builtin_erfc
6294 .{ .tag = @enumFromInt(561), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6295 // __builtin_erfcf
6296 .{ .tag = @enumFromInt(562), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6297 // __builtin_erfcf128
6298 .{ .tag = @enumFromInt(563), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6299 // __builtin_erfcl
6300 .{ .tag = @enumFromInt(564), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6301 // __builtin_erff
6302 .{ .tag = @enumFromInt(565), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6303 // __builtin_erff128
6304 .{ .tag = @enumFromInt(566), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6305 // __builtin_erfl
6306 .{ .tag = @enumFromInt(567), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6307 // __builtin_exp
6308 .{ .tag = @enumFromInt(568), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6309 // __builtin_exp10
6310 .{ .tag = @enumFromInt(569), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6311 // __builtin_exp10f
6312 .{ .tag = @enumFromInt(570), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6313 // __builtin_exp10f128
6314 .{ .tag = @enumFromInt(571), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6315 // __builtin_exp10f16
6316 .{ .tag = @enumFromInt(572), .properties = .{ .param_str = "hh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6317 // __builtin_exp10l
6318 .{ .tag = @enumFromInt(573), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6319 // __builtin_exp2
6320 .{ .tag = @enumFromInt(574), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6321 // __builtin_exp2f
6322 .{ .tag = @enumFromInt(575), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6323 // __builtin_exp2f128
6324 .{ .tag = @enumFromInt(576), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6325 // __builtin_exp2f16
6326 .{ .tag = @enumFromInt(577), .properties = .{ .param_str = "hh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6327 // __builtin_exp2l
6328 .{ .tag = @enumFromInt(578), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6329 // __builtin_expect
6330 .{ .tag = @enumFromInt(579), .properties = .{ .param_str = "LiLiLi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6331 // __builtin_expect_with_probability
6332 .{ .tag = @enumFromInt(580), .properties = .{ .param_str = "LiLiLid", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6333 // __builtin_expf
6334 .{ .tag = @enumFromInt(581), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6335 // __builtin_expf128
6336 .{ .tag = @enumFromInt(582), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6337 // __builtin_expf16
6338 .{ .tag = @enumFromInt(583), .properties = .{ .param_str = "hh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6339 // __builtin_expl
6340 .{ .tag = @enumFromInt(584), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6341 // __builtin_expm1
6342 .{ .tag = @enumFromInt(585), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6343 // __builtin_expm1f
6344 .{ .tag = @enumFromInt(586), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6345 // __builtin_expm1f128
6346 .{ .tag = @enumFromInt(587), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6347 // __builtin_expm1l
6348 .{ .tag = @enumFromInt(588), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6349 // __builtin_extend_pointer
6350 .{ .tag = @enumFromInt(589), .properties = .{ .param_str = "ULLiv*" } },
6351 // __builtin_extract_return_addr
6352 .{ .tag = @enumFromInt(590), .properties = .{ .param_str = "v*v*" } },
6353 // __builtin_fabs
6354 .{ .tag = @enumFromInt(591), .properties = .{ .param_str = "dd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6355 // __builtin_fabsf
6356 .{ .tag = @enumFromInt(592), .properties = .{ .param_str = "ff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6357 // __builtin_fabsf128
6358 .{ .tag = @enumFromInt(593), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6359 // __builtin_fabsf16
6360 .{ .tag = @enumFromInt(594), .properties = .{ .param_str = "hh", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6361 // __builtin_fabsl
6362 .{ .tag = @enumFromInt(595), .properties = .{ .param_str = "LdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6363 // __builtin_fdim
6364 .{ .tag = @enumFromInt(596), .properties = .{ .param_str = "ddd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6365 // __builtin_fdimf
6366 .{ .tag = @enumFromInt(597), .properties = .{ .param_str = "fff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6367 // __builtin_fdimf128
6368 .{ .tag = @enumFromInt(598), .properties = .{ .param_str = "LLdLLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6369 // __builtin_fdiml
6370 .{ .tag = @enumFromInt(599), .properties = .{ .param_str = "LdLdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6371 // __builtin_ffs
6372 .{ .tag = @enumFromInt(600), .properties = .{ .param_str = "ii", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6373 // __builtin_ffsl
6374 .{ .tag = @enumFromInt(601), .properties = .{ .param_str = "iLi", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6375 // __builtin_ffsll
6376 .{ .tag = @enumFromInt(602), .properties = .{ .param_str = "iLLi", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6377 // __builtin_floor
6378 .{ .tag = @enumFromInt(603), .properties = .{ .param_str = "dd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6379 // __builtin_floorf
6380 .{ .tag = @enumFromInt(604), .properties = .{ .param_str = "ff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6381 // __builtin_floorf128
6382 .{ .tag = @enumFromInt(605), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6383 // __builtin_floorf16
6384 .{ .tag = @enumFromInt(606), .properties = .{ .param_str = "hh", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6385 // __builtin_floorl
6386 .{ .tag = @enumFromInt(607), .properties = .{ .param_str = "LdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6387 // __builtin_flt_rounds
6388 .{ .tag = @enumFromInt(608), .properties = .{ .param_str = "i" } },
6389 // __builtin_fma
6390 .{ .tag = @enumFromInt(609), .properties = .{ .param_str = "dddd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6391 // __builtin_fmaf
6392 .{ .tag = @enumFromInt(610), .properties = .{ .param_str = "ffff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6393 // __builtin_fmaf128
6394 .{ .tag = @enumFromInt(611), .properties = .{ .param_str = "LLdLLdLLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6395 // __builtin_fmaf16
6396 .{ .tag = @enumFromInt(612), .properties = .{ .param_str = "hhhh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6397 // __builtin_fmal
6398 .{ .tag = @enumFromInt(613), .properties = .{ .param_str = "LdLdLdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6399 // __builtin_fmax
6400 .{ .tag = @enumFromInt(614), .properties = .{ .param_str = "ddd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6401 // __builtin_fmaxf
6402 .{ .tag = @enumFromInt(615), .properties = .{ .param_str = "fff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6403 // __builtin_fmaxf128
6404 .{ .tag = @enumFromInt(616), .properties = .{ .param_str = "LLdLLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6405 // __builtin_fmaxf16
6406 .{ .tag = @enumFromInt(617), .properties = .{ .param_str = "hhh", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6407 // __builtin_fmaxl
6408 .{ .tag = @enumFromInt(618), .properties = .{ .param_str = "LdLdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6409 // __builtin_fmin
6410 .{ .tag = @enumFromInt(619), .properties = .{ .param_str = "ddd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6411 // __builtin_fminf
6412 .{ .tag = @enumFromInt(620), .properties = .{ .param_str = "fff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6413 // __builtin_fminf128
6414 .{ .tag = @enumFromInt(621), .properties = .{ .param_str = "LLdLLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6415 // __builtin_fminf16
6416 .{ .tag = @enumFromInt(622), .properties = .{ .param_str = "hhh", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6417 // __builtin_fminl
6418 .{ .tag = @enumFromInt(623), .properties = .{ .param_str = "LdLdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6419 // __builtin_fmod
6420 .{ .tag = @enumFromInt(624), .properties = .{ .param_str = "ddd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6421 // __builtin_fmodf
6422 .{ .tag = @enumFromInt(625), .properties = .{ .param_str = "fff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6423 // __builtin_fmodf128
6424 .{ .tag = @enumFromInt(626), .properties = .{ .param_str = "LLdLLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6425 // __builtin_fmodf16
6426 .{ .tag = @enumFromInt(627), .properties = .{ .param_str = "hhh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6427 // __builtin_fmodl
6428 .{ .tag = @enumFromInt(628), .properties = .{ .param_str = "LdLdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6429 // __builtin_fpclassify
6430 .{ .tag = @enumFromInt(629), .properties = .{ .param_str = "iiiiii.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6431 // __builtin_fprintf
6432 .{ .tag = @enumFromInt(630), .properties = .{ .param_str = "iP*RcC*R.", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .printf, .format_string_position = 1 } } },
6433 // __builtin_frame_address
6434 .{ .tag = @enumFromInt(631), .properties = .{ .param_str = "v*IUi" } },
6435 // __builtin_free
6436 .{ .tag = @enumFromInt(632), .properties = .{ .param_str = "vv*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6437 // __builtin_frexp
6438 .{ .tag = @enumFromInt(633), .properties = .{ .param_str = "ddi*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6439 // __builtin_frexpf
6440 .{ .tag = @enumFromInt(634), .properties = .{ .param_str = "ffi*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6441 // __builtin_frexpf128
6442 .{ .tag = @enumFromInt(635), .properties = .{ .param_str = "LLdLLdi*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6443 // __builtin_frexpf16
6444 .{ .tag = @enumFromInt(636), .properties = .{ .param_str = "hhi*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6445 // __builtin_frexpl
6446 .{ .tag = @enumFromInt(637), .properties = .{ .param_str = "LdLdi*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6447 // __builtin_frob_return_addr
6448 .{ .tag = @enumFromInt(638), .properties = .{ .param_str = "v*v*" } },
6449 // __builtin_fscanf
6450 .{ .tag = @enumFromInt(639), .properties = .{ .param_str = "iP*RcC*R.", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .scanf, .format_string_position = 1 } } },
6451 // __builtin_getid
6452 .{ .tag = @enumFromInt(640), .properties = .{ .param_str = "Si", .target_set = TargetSet.initOne(.xcore), .attributes = .{ .@"const" = true } } },
6453 // __builtin_getps
6454 .{ .tag = @enumFromInt(641), .properties = .{ .param_str = "UiUi", .target_set = TargetSet.initOne(.xcore) } },
6455 // __builtin_huge_val
6456 .{ .tag = @enumFromInt(642), .properties = .{ .param_str = "d", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6457 // __builtin_huge_valf
6458 .{ .tag = @enumFromInt(643), .properties = .{ .param_str = "f", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6459 // __builtin_huge_valf128
6460 .{ .tag = @enumFromInt(644), .properties = .{ .param_str = "LLd", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6461 // __builtin_huge_valf16
6462 .{ .tag = @enumFromInt(645), .properties = .{ .param_str = "x", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6463 // __builtin_huge_vall
6464 .{ .tag = @enumFromInt(646), .properties = .{ .param_str = "Ld", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6465 // __builtin_hypot
6466 .{ .tag = @enumFromInt(647), .properties = .{ .param_str = "ddd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6467 // __builtin_hypotf
6468 .{ .tag = @enumFromInt(648), .properties = .{ .param_str = "fff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6469 // __builtin_hypotf128
6470 .{ .tag = @enumFromInt(649), .properties = .{ .param_str = "LLdLLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6471 // __builtin_hypotl
6472 .{ .tag = @enumFromInt(650), .properties = .{ .param_str = "LdLdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6473 // __builtin_ia32_rdpmc
6474 .{ .tag = @enumFromInt(651), .properties = .{ .param_str = "UOii", .target_set = TargetSet.initOne(.x86) } },
6475 // __builtin_ia32_rdtsc
6476 .{ .tag = @enumFromInt(652), .properties = .{ .param_str = "UOi", .target_set = TargetSet.initOne(.x86) } },
6477 // __builtin_ia32_rdtscp
6478 .{ .tag = @enumFromInt(653), .properties = .{ .param_str = "UOiUi*", .target_set = TargetSet.initOne(.x86) } },
6479 // __builtin_ilogb
6480 .{ .tag = @enumFromInt(654), .properties = .{ .param_str = "id", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6481 // __builtin_ilogbf
6482 .{ .tag = @enumFromInt(655), .properties = .{ .param_str = "if", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6483 // __builtin_ilogbf128
6484 .{ .tag = @enumFromInt(656), .properties = .{ .param_str = "iLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6485 // __builtin_ilogbl
6486 .{ .tag = @enumFromInt(657), .properties = .{ .param_str = "iLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6487 // __builtin_index
6488 .{ .tag = @enumFromInt(658), .properties = .{ .param_str = "c*cC*i", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6489 // __builtin_inf
6490 .{ .tag = @enumFromInt(659), .properties = .{ .param_str = "d", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6491 // __builtin_inff
6492 .{ .tag = @enumFromInt(660), .properties = .{ .param_str = "f", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6493 // __builtin_inff128
6494 .{ .tag = @enumFromInt(661), .properties = .{ .param_str = "LLd", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6495 // __builtin_inff16
6496 .{ .tag = @enumFromInt(662), .properties = .{ .param_str = "x", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6497 // __builtin_infl
6498 .{ .tag = @enumFromInt(663), .properties = .{ .param_str = "Ld", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
6499 // __builtin_init_dwarf_reg_size_table
6500 .{ .tag = @enumFromInt(664), .properties = .{ .param_str = "vv*" } },
6501 // __builtin_is_aligned
6502 .{ .tag = @enumFromInt(665), .properties = .{ .param_str = "bvC*z", .attributes = .{ .@"const" = true, .custom_typecheck = true, .const_evaluable = true } } },
6503 // __builtin_isfinite
6504 .{ .tag = @enumFromInt(666), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6505 // __builtin_isfpclass
6506 .{ .tag = @enumFromInt(667), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .const_evaluable = true } } },
6507 // __builtin_isgreater
6508 .{ .tag = @enumFromInt(668), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true } } },
6509 // __builtin_isgreaterequal
6510 .{ .tag = @enumFromInt(669), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true } } },
6511 // __builtin_isinf
6512 .{ .tag = @enumFromInt(670), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6513 // __builtin_isinf_sign
6514 .{ .tag = @enumFromInt(671), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6515 // __builtin_isless
6516 .{ .tag = @enumFromInt(672), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true } } },
6517 // __builtin_islessequal
6518 .{ .tag = @enumFromInt(673), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true } } },
6519 // __builtin_islessgreater
6520 .{ .tag = @enumFromInt(674), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true } } },
6521 // __builtin_isnan
6522 .{ .tag = @enumFromInt(675), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6523 // __builtin_isnormal
6524 .{ .tag = @enumFromInt(676), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6525 // __builtin_isunordered
6526 .{ .tag = @enumFromInt(677), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true } } },
6527 // __builtin_labs
6528 .{ .tag = @enumFromInt(678), .properties = .{ .param_str = "LiLi", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6529 // __builtin_launder
6530 .{ .tag = @enumFromInt(679), .properties = .{ .param_str = "v*v*", .attributes = .{ .custom_typecheck = true, .const_evaluable = true } } },
6531 // __builtin_ldexp
6532 .{ .tag = @enumFromInt(680), .properties = .{ .param_str = "ddi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6533 // __builtin_ldexpf
6534 .{ .tag = @enumFromInt(681), .properties = .{ .param_str = "ffi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6535 // __builtin_ldexpf128
6536 .{ .tag = @enumFromInt(682), .properties = .{ .param_str = "LLdLLdi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6537 // __builtin_ldexpf16
6538 .{ .tag = @enumFromInt(683), .properties = .{ .param_str = "hhi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6539 // __builtin_ldexpl
6540 .{ .tag = @enumFromInt(684), .properties = .{ .param_str = "LdLdi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6541 // __builtin_lgamma
6542 .{ .tag = @enumFromInt(685), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6543 // __builtin_lgammaf
6544 .{ .tag = @enumFromInt(686), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6545 // __builtin_lgammaf128
6546 .{ .tag = @enumFromInt(687), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6547 // __builtin_lgammal
6548 .{ .tag = @enumFromInt(688), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6549 // __builtin_llabs
6550 .{ .tag = @enumFromInt(689), .properties = .{ .param_str = "LLiLLi", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
6551 // __builtin_llrint
6552 .{ .tag = @enumFromInt(690), .properties = .{ .param_str = "LLid", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6553 // __builtin_llrintf
6554 .{ .tag = @enumFromInt(691), .properties = .{ .param_str = "LLif", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6555 // __builtin_llrintf128
6556 .{ .tag = @enumFromInt(692), .properties = .{ .param_str = "LLiLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6557 // __builtin_llrintl
6558 .{ .tag = @enumFromInt(693), .properties = .{ .param_str = "LLiLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6559 // __builtin_llround
6560 .{ .tag = @enumFromInt(694), .properties = .{ .param_str = "LLid", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6561 // __builtin_llroundf
6562 .{ .tag = @enumFromInt(695), .properties = .{ .param_str = "LLif", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6563 // __builtin_llroundf128
6564 .{ .tag = @enumFromInt(696), .properties = .{ .param_str = "LLiLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6565 // __builtin_llroundl
6566 .{ .tag = @enumFromInt(697), .properties = .{ .param_str = "LLiLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6567 // __builtin_log
6568 .{ .tag = @enumFromInt(698), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6569 // __builtin_log10
6570 .{ .tag = @enumFromInt(699), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6571 // __builtin_log10f
6572 .{ .tag = @enumFromInt(700), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6573 // __builtin_log10f128
6574 .{ .tag = @enumFromInt(701), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6575 // __builtin_log10f16
6576 .{ .tag = @enumFromInt(702), .properties = .{ .param_str = "hh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6577 // __builtin_log10l
6578 .{ .tag = @enumFromInt(703), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6579 // __builtin_log1p
6580 .{ .tag = @enumFromInt(704), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6581 // __builtin_log1pf
6582 .{ .tag = @enumFromInt(705), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6583 // __builtin_log1pf128
6584 .{ .tag = @enumFromInt(706), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6585 // __builtin_log1pl
6586 .{ .tag = @enumFromInt(707), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6587 // __builtin_log2
6588 .{ .tag = @enumFromInt(708), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6589 // __builtin_log2f
6590 .{ .tag = @enumFromInt(709), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6591 // __builtin_log2f128
6592 .{ .tag = @enumFromInt(710), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6593 // __builtin_log2f16
6594 .{ .tag = @enumFromInt(711), .properties = .{ .param_str = "hh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6595 // __builtin_log2l
6596 .{ .tag = @enumFromInt(712), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6597 // __builtin_logb
6598 .{ .tag = @enumFromInt(713), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6599 // __builtin_logbf
6600 .{ .tag = @enumFromInt(714), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6601 // __builtin_logbf128
6602 .{ .tag = @enumFromInt(715), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6603 // __builtin_logbl
6604 .{ .tag = @enumFromInt(716), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6605 // __builtin_logf
6606 .{ .tag = @enumFromInt(717), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6607 // __builtin_logf128
6608 .{ .tag = @enumFromInt(718), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6609 // __builtin_logf16
6610 .{ .tag = @enumFromInt(719), .properties = .{ .param_str = "hh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6611 // __builtin_logl
6612 .{ .tag = @enumFromInt(720), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6613 // __builtin_longjmp
6614 .{ .tag = @enumFromInt(721), .properties = .{ .param_str = "vv**i", .attributes = .{ .noreturn = true } } },
6615 // __builtin_lrint
6616 .{ .tag = @enumFromInt(722), .properties = .{ .param_str = "Lid", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6617 // __builtin_lrintf
6618 .{ .tag = @enumFromInt(723), .properties = .{ .param_str = "Lif", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6619 // __builtin_lrintf128
6620 .{ .tag = @enumFromInt(724), .properties = .{ .param_str = "LiLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6621 // __builtin_lrintl
6622 .{ .tag = @enumFromInt(725), .properties = .{ .param_str = "LiLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6623 // __builtin_lround
6624 .{ .tag = @enumFromInt(726), .properties = .{ .param_str = "Lid", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6625 // __builtin_lroundf
6626 .{ .tag = @enumFromInt(727), .properties = .{ .param_str = "Lif", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6627 // __builtin_lroundf128
6628 .{ .tag = @enumFromInt(728), .properties = .{ .param_str = "LiLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6629 // __builtin_lroundl
6630 .{ .tag = @enumFromInt(729), .properties = .{ .param_str = "LiLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
6631 // __builtin_malloc
6632 .{ .tag = @enumFromInt(730), .properties = .{ .param_str = "v*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6633 // __builtin_matrix_column_major_load
6634 .{ .tag = @enumFromInt(731), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true, .lib_function_with_builtin_prefix = true } } },
6635 // __builtin_matrix_column_major_store
6636 .{ .tag = @enumFromInt(732), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true, .lib_function_with_builtin_prefix = true } } },
6637 // __builtin_matrix_transpose
6638 .{ .tag = @enumFromInt(733), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true, .lib_function_with_builtin_prefix = true } } },
6639 // __builtin_memchr
6640 .{ .tag = @enumFromInt(734), .properties = .{ .param_str = "v*vC*iz", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6641 // __builtin_memcmp
6642 .{ .tag = @enumFromInt(735), .properties = .{ .param_str = "ivC*vC*z", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6643 // __builtin_memcpy
6644 .{ .tag = @enumFromInt(736), .properties = .{ .param_str = "v*v*vC*z", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6645 // __builtin_memcpy_inline
6646 .{ .tag = @enumFromInt(737), .properties = .{ .param_str = "vv*vC*Iz" } },
6647 // __builtin_memmove
6648 .{ .tag = @enumFromInt(738), .properties = .{ .param_str = "v*v*vC*z", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
6649 // __builtin_mempcpy
6650 .{ .tag = @enumFromInt(739), .properties = .{ .param_str = "v*v*vC*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6651 // __builtin_memset
6652 .{ .tag = @enumFromInt(740), .properties = .{ .param_str = "v*v*iz", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6653 // __builtin_memset_inline
6654 .{ .tag = @enumFromInt(741), .properties = .{ .param_str = "vv*iIz" } },
6655 // __builtin_mips_absq_s_ph
6656 .{ .tag = @enumFromInt(742), .properties = .{ .param_str = "V2sV2s", .target_set = TargetSet.initOne(.mips) } },
6657 // __builtin_mips_absq_s_qb
6658 .{ .tag = @enumFromInt(743), .properties = .{ .param_str = "V4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6659 // __builtin_mips_absq_s_w
6660 .{ .tag = @enumFromInt(744), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.mips) } },
6661 // __builtin_mips_addq_ph
6662 .{ .tag = @enumFromInt(745), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6663 // __builtin_mips_addq_s_ph
6664 .{ .tag = @enumFromInt(746), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6665 // __builtin_mips_addq_s_w
6666 .{ .tag = @enumFromInt(747), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips) } },
6667 // __builtin_mips_addqh_ph
6668 .{ .tag = @enumFromInt(748), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6669 // __builtin_mips_addqh_r_ph
6670 .{ .tag = @enumFromInt(749), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6671 // __builtin_mips_addqh_r_w
6672 .{ .tag = @enumFromInt(750), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6673 // __builtin_mips_addqh_w
6674 .{ .tag = @enumFromInt(751), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6675 // __builtin_mips_addsc
6676 .{ .tag = @enumFromInt(752), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips) } },
6677 // __builtin_mips_addu_ph
6678 .{ .tag = @enumFromInt(753), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6679 // __builtin_mips_addu_qb
6680 .{ .tag = @enumFromInt(754), .properties = .{ .param_str = "V4ScV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6681 // __builtin_mips_addu_s_ph
6682 .{ .tag = @enumFromInt(755), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6683 // __builtin_mips_addu_s_qb
6684 .{ .tag = @enumFromInt(756), .properties = .{ .param_str = "V4ScV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6685 // __builtin_mips_adduh_qb
6686 .{ .tag = @enumFromInt(757), .properties = .{ .param_str = "V4ScV4ScV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6687 // __builtin_mips_adduh_r_qb
6688 .{ .tag = @enumFromInt(758), .properties = .{ .param_str = "V4ScV4ScV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6689 // __builtin_mips_addwc
6690 .{ .tag = @enumFromInt(759), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips) } },
6691 // __builtin_mips_append
6692 .{ .tag = @enumFromInt(760), .properties = .{ .param_str = "iiiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6693 // __builtin_mips_balign
6694 .{ .tag = @enumFromInt(761), .properties = .{ .param_str = "iiiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6695 // __builtin_mips_bitrev
6696 .{ .tag = @enumFromInt(762), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6697 // __builtin_mips_bposge32
6698 .{ .tag = @enumFromInt(763), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.mips) } },
6699 // __builtin_mips_cmp_eq_ph
6700 .{ .tag = @enumFromInt(764), .properties = .{ .param_str = "vV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6701 // __builtin_mips_cmp_le_ph
6702 .{ .tag = @enumFromInt(765), .properties = .{ .param_str = "vV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6703 // __builtin_mips_cmp_lt_ph
6704 .{ .tag = @enumFromInt(766), .properties = .{ .param_str = "vV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6705 // __builtin_mips_cmpgdu_eq_qb
6706 .{ .tag = @enumFromInt(767), .properties = .{ .param_str = "iV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6707 // __builtin_mips_cmpgdu_le_qb
6708 .{ .tag = @enumFromInt(768), .properties = .{ .param_str = "iV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6709 // __builtin_mips_cmpgdu_lt_qb
6710 .{ .tag = @enumFromInt(769), .properties = .{ .param_str = "iV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6711 // __builtin_mips_cmpgu_eq_qb
6712 .{ .tag = @enumFromInt(770), .properties = .{ .param_str = "iV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6713 // __builtin_mips_cmpgu_le_qb
6714 .{ .tag = @enumFromInt(771), .properties = .{ .param_str = "iV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6715 // __builtin_mips_cmpgu_lt_qb
6716 .{ .tag = @enumFromInt(772), .properties = .{ .param_str = "iV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6717 // __builtin_mips_cmpu_eq_qb
6718 .{ .tag = @enumFromInt(773), .properties = .{ .param_str = "vV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6719 // __builtin_mips_cmpu_le_qb
6720 .{ .tag = @enumFromInt(774), .properties = .{ .param_str = "vV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6721 // __builtin_mips_cmpu_lt_qb
6722 .{ .tag = @enumFromInt(775), .properties = .{ .param_str = "vV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6723 // __builtin_mips_dpa_w_ph
6724 .{ .tag = @enumFromInt(776), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6725 // __builtin_mips_dpaq_s_w_ph
6726 .{ .tag = @enumFromInt(777), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6727 // __builtin_mips_dpaq_sa_l_w
6728 .{ .tag = @enumFromInt(778), .properties = .{ .param_str = "LLiLLiii", .target_set = TargetSet.initOne(.mips) } },
6729 // __builtin_mips_dpaqx_s_w_ph
6730 .{ .tag = @enumFromInt(779), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6731 // __builtin_mips_dpaqx_sa_w_ph
6732 .{ .tag = @enumFromInt(780), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6733 // __builtin_mips_dpau_h_qbl
6734 .{ .tag = @enumFromInt(781), .properties = .{ .param_str = "LLiLLiV4ScV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6735 // __builtin_mips_dpau_h_qbr
6736 .{ .tag = @enumFromInt(782), .properties = .{ .param_str = "LLiLLiV4ScV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6737 // __builtin_mips_dpax_w_ph
6738 .{ .tag = @enumFromInt(783), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6739 // __builtin_mips_dps_w_ph
6740 .{ .tag = @enumFromInt(784), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6741 // __builtin_mips_dpsq_s_w_ph
6742 .{ .tag = @enumFromInt(785), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6743 // __builtin_mips_dpsq_sa_l_w
6744 .{ .tag = @enumFromInt(786), .properties = .{ .param_str = "LLiLLiii", .target_set = TargetSet.initOne(.mips) } },
6745 // __builtin_mips_dpsqx_s_w_ph
6746 .{ .tag = @enumFromInt(787), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6747 // __builtin_mips_dpsqx_sa_w_ph
6748 .{ .tag = @enumFromInt(788), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6749 // __builtin_mips_dpsu_h_qbl
6750 .{ .tag = @enumFromInt(789), .properties = .{ .param_str = "LLiLLiV4ScV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6751 // __builtin_mips_dpsu_h_qbr
6752 .{ .tag = @enumFromInt(790), .properties = .{ .param_str = "LLiLLiV4ScV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6753 // __builtin_mips_dpsx_w_ph
6754 .{ .tag = @enumFromInt(791), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6755 // __builtin_mips_extp
6756 .{ .tag = @enumFromInt(792), .properties = .{ .param_str = "iLLii", .target_set = TargetSet.initOne(.mips) } },
6757 // __builtin_mips_extpdp
6758 .{ .tag = @enumFromInt(793), .properties = .{ .param_str = "iLLii", .target_set = TargetSet.initOne(.mips) } },
6759 // __builtin_mips_extr_r_w
6760 .{ .tag = @enumFromInt(794), .properties = .{ .param_str = "iLLii", .target_set = TargetSet.initOne(.mips) } },
6761 // __builtin_mips_extr_rs_w
6762 .{ .tag = @enumFromInt(795), .properties = .{ .param_str = "iLLii", .target_set = TargetSet.initOne(.mips) } },
6763 // __builtin_mips_extr_s_h
6764 .{ .tag = @enumFromInt(796), .properties = .{ .param_str = "iLLii", .target_set = TargetSet.initOne(.mips) } },
6765 // __builtin_mips_extr_w
6766 .{ .tag = @enumFromInt(797), .properties = .{ .param_str = "iLLii", .target_set = TargetSet.initOne(.mips) } },
6767 // __builtin_mips_insv
6768 .{ .tag = @enumFromInt(798), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips) } },
6769 // __builtin_mips_lbux
6770 .{ .tag = @enumFromInt(799), .properties = .{ .param_str = "iv*i", .target_set = TargetSet.initOne(.mips) } },
6771 // __builtin_mips_lhx
6772 .{ .tag = @enumFromInt(800), .properties = .{ .param_str = "iv*i", .target_set = TargetSet.initOne(.mips) } },
6773 // __builtin_mips_lwx
6774 .{ .tag = @enumFromInt(801), .properties = .{ .param_str = "iv*i", .target_set = TargetSet.initOne(.mips) } },
6775 // __builtin_mips_madd
6776 .{ .tag = @enumFromInt(802), .properties = .{ .param_str = "LLiLLiii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6777 // __builtin_mips_maddu
6778 .{ .tag = @enumFromInt(803), .properties = .{ .param_str = "LLiLLiUiUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6779 // __builtin_mips_maq_s_w_phl
6780 .{ .tag = @enumFromInt(804), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6781 // __builtin_mips_maq_s_w_phr
6782 .{ .tag = @enumFromInt(805), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6783 // __builtin_mips_maq_sa_w_phl
6784 .{ .tag = @enumFromInt(806), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6785 // __builtin_mips_maq_sa_w_phr
6786 .{ .tag = @enumFromInt(807), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6787 // __builtin_mips_modsub
6788 .{ .tag = @enumFromInt(808), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6789 // __builtin_mips_msub
6790 .{ .tag = @enumFromInt(809), .properties = .{ .param_str = "LLiLLiii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6791 // __builtin_mips_msubu
6792 .{ .tag = @enumFromInt(810), .properties = .{ .param_str = "LLiLLiUiUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6793 // __builtin_mips_mthlip
6794 .{ .tag = @enumFromInt(811), .properties = .{ .param_str = "LLiLLii", .target_set = TargetSet.initOne(.mips) } },
6795 // __builtin_mips_mul_ph
6796 .{ .tag = @enumFromInt(812), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6797 // __builtin_mips_mul_s_ph
6798 .{ .tag = @enumFromInt(813), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6799 // __builtin_mips_muleq_s_w_phl
6800 .{ .tag = @enumFromInt(814), .properties = .{ .param_str = "iV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6801 // __builtin_mips_muleq_s_w_phr
6802 .{ .tag = @enumFromInt(815), .properties = .{ .param_str = "iV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6803 // __builtin_mips_muleu_s_ph_qbl
6804 .{ .tag = @enumFromInt(816), .properties = .{ .param_str = "V2sV4ScV2s", .target_set = TargetSet.initOne(.mips) } },
6805 // __builtin_mips_muleu_s_ph_qbr
6806 .{ .tag = @enumFromInt(817), .properties = .{ .param_str = "V2sV4ScV2s", .target_set = TargetSet.initOne(.mips) } },
6807 // __builtin_mips_mulq_rs_ph
6808 .{ .tag = @enumFromInt(818), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6809 // __builtin_mips_mulq_rs_w
6810 .{ .tag = @enumFromInt(819), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips) } },
6811 // __builtin_mips_mulq_s_ph
6812 .{ .tag = @enumFromInt(820), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6813 // __builtin_mips_mulq_s_w
6814 .{ .tag = @enumFromInt(821), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips) } },
6815 // __builtin_mips_mulsa_w_ph
6816 .{ .tag = @enumFromInt(822), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6817 // __builtin_mips_mulsaq_s_w_ph
6818 .{ .tag = @enumFromInt(823), .properties = .{ .param_str = "LLiLLiV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6819 // __builtin_mips_mult
6820 .{ .tag = @enumFromInt(824), .properties = .{ .param_str = "LLiii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6821 // __builtin_mips_multu
6822 .{ .tag = @enumFromInt(825), .properties = .{ .param_str = "LLiUiUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6823 // __builtin_mips_packrl_ph
6824 .{ .tag = @enumFromInt(826), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6825 // __builtin_mips_pick_ph
6826 .{ .tag = @enumFromInt(827), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6827 // __builtin_mips_pick_qb
6828 .{ .tag = @enumFromInt(828), .properties = .{ .param_str = "V4ScV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6829 // __builtin_mips_preceq_w_phl
6830 .{ .tag = @enumFromInt(829), .properties = .{ .param_str = "iV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6831 // __builtin_mips_preceq_w_phr
6832 .{ .tag = @enumFromInt(830), .properties = .{ .param_str = "iV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6833 // __builtin_mips_precequ_ph_qbl
6834 .{ .tag = @enumFromInt(831), .properties = .{ .param_str = "V2sV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6835 // __builtin_mips_precequ_ph_qbla
6836 .{ .tag = @enumFromInt(832), .properties = .{ .param_str = "V2sV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6837 // __builtin_mips_precequ_ph_qbr
6838 .{ .tag = @enumFromInt(833), .properties = .{ .param_str = "V2sV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6839 // __builtin_mips_precequ_ph_qbra
6840 .{ .tag = @enumFromInt(834), .properties = .{ .param_str = "V2sV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6841 // __builtin_mips_preceu_ph_qbl
6842 .{ .tag = @enumFromInt(835), .properties = .{ .param_str = "V2sV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6843 // __builtin_mips_preceu_ph_qbla
6844 .{ .tag = @enumFromInt(836), .properties = .{ .param_str = "V2sV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6845 // __builtin_mips_preceu_ph_qbr
6846 .{ .tag = @enumFromInt(837), .properties = .{ .param_str = "V2sV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6847 // __builtin_mips_preceu_ph_qbra
6848 .{ .tag = @enumFromInt(838), .properties = .{ .param_str = "V2sV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6849 // __builtin_mips_precr_qb_ph
6850 .{ .tag = @enumFromInt(839), .properties = .{ .param_str = "V4ScV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6851 // __builtin_mips_precr_sra_ph_w
6852 .{ .tag = @enumFromInt(840), .properties = .{ .param_str = "V2siiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6853 // __builtin_mips_precr_sra_r_ph_w
6854 .{ .tag = @enumFromInt(841), .properties = .{ .param_str = "V2siiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6855 // __builtin_mips_precrq_ph_w
6856 .{ .tag = @enumFromInt(842), .properties = .{ .param_str = "V2sii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6857 // __builtin_mips_precrq_qb_ph
6858 .{ .tag = @enumFromInt(843), .properties = .{ .param_str = "V4ScV2sV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6859 // __builtin_mips_precrq_rs_ph_w
6860 .{ .tag = @enumFromInt(844), .properties = .{ .param_str = "V2sii", .target_set = TargetSet.initOne(.mips) } },
6861 // __builtin_mips_precrqu_s_qb_ph
6862 .{ .tag = @enumFromInt(845), .properties = .{ .param_str = "V4ScV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6863 // __builtin_mips_prepend
6864 .{ .tag = @enumFromInt(846), .properties = .{ .param_str = "iiiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6865 // __builtin_mips_raddu_w_qb
6866 .{ .tag = @enumFromInt(847), .properties = .{ .param_str = "iV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6867 // __builtin_mips_rddsp
6868 .{ .tag = @enumFromInt(848), .properties = .{ .param_str = "iIi", .target_set = TargetSet.initOne(.mips) } },
6869 // __builtin_mips_repl_ph
6870 .{ .tag = @enumFromInt(849), .properties = .{ .param_str = "V2si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6871 // __builtin_mips_repl_qb
6872 .{ .tag = @enumFromInt(850), .properties = .{ .param_str = "V4Sci", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6873 // __builtin_mips_shilo
6874 .{ .tag = @enumFromInt(851), .properties = .{ .param_str = "LLiLLii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6875 // __builtin_mips_shll_ph
6876 .{ .tag = @enumFromInt(852), .properties = .{ .param_str = "V2sV2si", .target_set = TargetSet.initOne(.mips) } },
6877 // __builtin_mips_shll_qb
6878 .{ .tag = @enumFromInt(853), .properties = .{ .param_str = "V4ScV4Sci", .target_set = TargetSet.initOne(.mips) } },
6879 // __builtin_mips_shll_s_ph
6880 .{ .tag = @enumFromInt(854), .properties = .{ .param_str = "V2sV2si", .target_set = TargetSet.initOne(.mips) } },
6881 // __builtin_mips_shll_s_w
6882 .{ .tag = @enumFromInt(855), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips) } },
6883 // __builtin_mips_shra_ph
6884 .{ .tag = @enumFromInt(856), .properties = .{ .param_str = "V2sV2si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6885 // __builtin_mips_shra_qb
6886 .{ .tag = @enumFromInt(857), .properties = .{ .param_str = "V4ScV4Sci", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6887 // __builtin_mips_shra_r_ph
6888 .{ .tag = @enumFromInt(858), .properties = .{ .param_str = "V2sV2si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6889 // __builtin_mips_shra_r_qb
6890 .{ .tag = @enumFromInt(859), .properties = .{ .param_str = "V4ScV4Sci", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6891 // __builtin_mips_shra_r_w
6892 .{ .tag = @enumFromInt(860), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6893 // __builtin_mips_shrl_ph
6894 .{ .tag = @enumFromInt(861), .properties = .{ .param_str = "V2sV2si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6895 // __builtin_mips_shrl_qb
6896 .{ .tag = @enumFromInt(862), .properties = .{ .param_str = "V4ScV4Sci", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6897 // __builtin_mips_subq_ph
6898 .{ .tag = @enumFromInt(863), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6899 // __builtin_mips_subq_s_ph
6900 .{ .tag = @enumFromInt(864), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6901 // __builtin_mips_subq_s_w
6902 .{ .tag = @enumFromInt(865), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips) } },
6903 // __builtin_mips_subqh_ph
6904 .{ .tag = @enumFromInt(866), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6905 // __builtin_mips_subqh_r_ph
6906 .{ .tag = @enumFromInt(867), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6907 // __builtin_mips_subqh_r_w
6908 .{ .tag = @enumFromInt(868), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6909 // __builtin_mips_subqh_w
6910 .{ .tag = @enumFromInt(869), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6911 // __builtin_mips_subu_ph
6912 .{ .tag = @enumFromInt(870), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6913 // __builtin_mips_subu_qb
6914 .{ .tag = @enumFromInt(871), .properties = .{ .param_str = "V4ScV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6915 // __builtin_mips_subu_s_ph
6916 .{ .tag = @enumFromInt(872), .properties = .{ .param_str = "V2sV2sV2s", .target_set = TargetSet.initOne(.mips) } },
6917 // __builtin_mips_subu_s_qb
6918 .{ .tag = @enumFromInt(873), .properties = .{ .param_str = "V4ScV4ScV4Sc", .target_set = TargetSet.initOne(.mips) } },
6919 // __builtin_mips_subuh_qb
6920 .{ .tag = @enumFromInt(874), .properties = .{ .param_str = "V4ScV4ScV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6921 // __builtin_mips_subuh_r_qb
6922 .{ .tag = @enumFromInt(875), .properties = .{ .param_str = "V4ScV4ScV4Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6923 // __builtin_mips_wrdsp
6924 .{ .tag = @enumFromInt(876), .properties = .{ .param_str = "viIi", .target_set = TargetSet.initOne(.mips) } },
6925 // __builtin_modf
6926 .{ .tag = @enumFromInt(877), .properties = .{ .param_str = "ddd*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6927 // __builtin_modff
6928 .{ .tag = @enumFromInt(878), .properties = .{ .param_str = "fff*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6929 // __builtin_modff128
6930 .{ .tag = @enumFromInt(879), .properties = .{ .param_str = "LLdLLdLLd*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6931 // __builtin_modfl
6932 .{ .tag = @enumFromInt(880), .properties = .{ .param_str = "LdLdLd*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
6933 // __builtin_msa_add_a_b
6934 .{ .tag = @enumFromInt(881), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6935 // __builtin_msa_add_a_d
6936 .{ .tag = @enumFromInt(882), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6937 // __builtin_msa_add_a_h
6938 .{ .tag = @enumFromInt(883), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6939 // __builtin_msa_add_a_w
6940 .{ .tag = @enumFromInt(884), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6941 // __builtin_msa_adds_a_b
6942 .{ .tag = @enumFromInt(885), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6943 // __builtin_msa_adds_a_d
6944 .{ .tag = @enumFromInt(886), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6945 // __builtin_msa_adds_a_h
6946 .{ .tag = @enumFromInt(887), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6947 // __builtin_msa_adds_a_w
6948 .{ .tag = @enumFromInt(888), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6949 // __builtin_msa_adds_s_b
6950 .{ .tag = @enumFromInt(889), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6951 // __builtin_msa_adds_s_d
6952 .{ .tag = @enumFromInt(890), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6953 // __builtin_msa_adds_s_h
6954 .{ .tag = @enumFromInt(891), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6955 // __builtin_msa_adds_s_w
6956 .{ .tag = @enumFromInt(892), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6957 // __builtin_msa_adds_u_b
6958 .{ .tag = @enumFromInt(893), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6959 // __builtin_msa_adds_u_d
6960 .{ .tag = @enumFromInt(894), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6961 // __builtin_msa_adds_u_h
6962 .{ .tag = @enumFromInt(895), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6963 // __builtin_msa_adds_u_w
6964 .{ .tag = @enumFromInt(896), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6965 // __builtin_msa_addv_b
6966 .{ .tag = @enumFromInt(897), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6967 // __builtin_msa_addv_d
6968 .{ .tag = @enumFromInt(898), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6969 // __builtin_msa_addv_h
6970 .{ .tag = @enumFromInt(899), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6971 // __builtin_msa_addv_w
6972 .{ .tag = @enumFromInt(900), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6973 // __builtin_msa_addvi_b
6974 .{ .tag = @enumFromInt(901), .properties = .{ .param_str = "V16cV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6975 // __builtin_msa_addvi_d
6976 .{ .tag = @enumFromInt(902), .properties = .{ .param_str = "V2LLiV2LLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6977 // __builtin_msa_addvi_h
6978 .{ .tag = @enumFromInt(903), .properties = .{ .param_str = "V8sV8sIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6979 // __builtin_msa_addvi_w
6980 .{ .tag = @enumFromInt(904), .properties = .{ .param_str = "V4iV4iIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6981 // __builtin_msa_and_v
6982 .{ .tag = @enumFromInt(905), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6983 // __builtin_msa_andi_b
6984 .{ .tag = @enumFromInt(906), .properties = .{ .param_str = "V16UcV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6985 // __builtin_msa_asub_s_b
6986 .{ .tag = @enumFromInt(907), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6987 // __builtin_msa_asub_s_d
6988 .{ .tag = @enumFromInt(908), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6989 // __builtin_msa_asub_s_h
6990 .{ .tag = @enumFromInt(909), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6991 // __builtin_msa_asub_s_w
6992 .{ .tag = @enumFromInt(910), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6993 // __builtin_msa_asub_u_b
6994 .{ .tag = @enumFromInt(911), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6995 // __builtin_msa_asub_u_d
6996 .{ .tag = @enumFromInt(912), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6997 // __builtin_msa_asub_u_h
6998 .{ .tag = @enumFromInt(913), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
6999 // __builtin_msa_asub_u_w
7000 .{ .tag = @enumFromInt(914), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7001 // __builtin_msa_ave_s_b
7002 .{ .tag = @enumFromInt(915), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7003 // __builtin_msa_ave_s_d
7004 .{ .tag = @enumFromInt(916), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7005 // __builtin_msa_ave_s_h
7006 .{ .tag = @enumFromInt(917), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7007 // __builtin_msa_ave_s_w
7008 .{ .tag = @enumFromInt(918), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7009 // __builtin_msa_ave_u_b
7010 .{ .tag = @enumFromInt(919), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7011 // __builtin_msa_ave_u_d
7012 .{ .tag = @enumFromInt(920), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7013 // __builtin_msa_ave_u_h
7014 .{ .tag = @enumFromInt(921), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7015 // __builtin_msa_ave_u_w
7016 .{ .tag = @enumFromInt(922), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7017 // __builtin_msa_aver_s_b
7018 .{ .tag = @enumFromInt(923), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7019 // __builtin_msa_aver_s_d
7020 .{ .tag = @enumFromInt(924), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7021 // __builtin_msa_aver_s_h
7022 .{ .tag = @enumFromInt(925), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7023 // __builtin_msa_aver_s_w
7024 .{ .tag = @enumFromInt(926), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7025 // __builtin_msa_aver_u_b
7026 .{ .tag = @enumFromInt(927), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7027 // __builtin_msa_aver_u_d
7028 .{ .tag = @enumFromInt(928), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7029 // __builtin_msa_aver_u_h
7030 .{ .tag = @enumFromInt(929), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7031 // __builtin_msa_aver_u_w
7032 .{ .tag = @enumFromInt(930), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7033 // __builtin_msa_bclr_b
7034 .{ .tag = @enumFromInt(931), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7035 // __builtin_msa_bclr_d
7036 .{ .tag = @enumFromInt(932), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7037 // __builtin_msa_bclr_h
7038 .{ .tag = @enumFromInt(933), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7039 // __builtin_msa_bclr_w
7040 .{ .tag = @enumFromInt(934), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7041 // __builtin_msa_bclri_b
7042 .{ .tag = @enumFromInt(935), .properties = .{ .param_str = "V16UcV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7043 // __builtin_msa_bclri_d
7044 .{ .tag = @enumFromInt(936), .properties = .{ .param_str = "V2ULLiV2ULLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7045 // __builtin_msa_bclri_h
7046 .{ .tag = @enumFromInt(937), .properties = .{ .param_str = "V8UsV8UsIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7047 // __builtin_msa_bclri_w
7048 .{ .tag = @enumFromInt(938), .properties = .{ .param_str = "V4UiV4UiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7049 // __builtin_msa_binsl_b
7050 .{ .tag = @enumFromInt(939), .properties = .{ .param_str = "V16UcV16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7051 // __builtin_msa_binsl_d
7052 .{ .tag = @enumFromInt(940), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7053 // __builtin_msa_binsl_h
7054 .{ .tag = @enumFromInt(941), .properties = .{ .param_str = "V8UsV8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7055 // __builtin_msa_binsl_w
7056 .{ .tag = @enumFromInt(942), .properties = .{ .param_str = "V4UiV4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7057 // __builtin_msa_binsli_b
7058 .{ .tag = @enumFromInt(943), .properties = .{ .param_str = "V16UcV16UcV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7059 // __builtin_msa_binsli_d
7060 .{ .tag = @enumFromInt(944), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7061 // __builtin_msa_binsli_h
7062 .{ .tag = @enumFromInt(945), .properties = .{ .param_str = "V8UsV8UsV8UsIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7063 // __builtin_msa_binsli_w
7064 .{ .tag = @enumFromInt(946), .properties = .{ .param_str = "V4UiV4UiV4UiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7065 // __builtin_msa_binsr_b
7066 .{ .tag = @enumFromInt(947), .properties = .{ .param_str = "V16UcV16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7067 // __builtin_msa_binsr_d
7068 .{ .tag = @enumFromInt(948), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7069 // __builtin_msa_binsr_h
7070 .{ .tag = @enumFromInt(949), .properties = .{ .param_str = "V8UsV8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7071 // __builtin_msa_binsr_w
7072 .{ .tag = @enumFromInt(950), .properties = .{ .param_str = "V4UiV4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7073 // __builtin_msa_binsri_b
7074 .{ .tag = @enumFromInt(951), .properties = .{ .param_str = "V16UcV16UcV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7075 // __builtin_msa_binsri_d
7076 .{ .tag = @enumFromInt(952), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7077 // __builtin_msa_binsri_h
7078 .{ .tag = @enumFromInt(953), .properties = .{ .param_str = "V8UsV8UsV8UsIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7079 // __builtin_msa_binsri_w
7080 .{ .tag = @enumFromInt(954), .properties = .{ .param_str = "V4UiV4UiV4UiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7081 // __builtin_msa_bmnz_v
7082 .{ .tag = @enumFromInt(955), .properties = .{ .param_str = "V16UcV16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7083 // __builtin_msa_bmnzi_b
7084 .{ .tag = @enumFromInt(956), .properties = .{ .param_str = "V16UcV16UcV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7085 // __builtin_msa_bmz_v
7086 .{ .tag = @enumFromInt(957), .properties = .{ .param_str = "V16UcV16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7087 // __builtin_msa_bmzi_b
7088 .{ .tag = @enumFromInt(958), .properties = .{ .param_str = "V16UcV16UcV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7089 // __builtin_msa_bneg_b
7090 .{ .tag = @enumFromInt(959), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7091 // __builtin_msa_bneg_d
7092 .{ .tag = @enumFromInt(960), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7093 // __builtin_msa_bneg_h
7094 .{ .tag = @enumFromInt(961), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7095 // __builtin_msa_bneg_w
7096 .{ .tag = @enumFromInt(962), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7097 // __builtin_msa_bnegi_b
7098 .{ .tag = @enumFromInt(963), .properties = .{ .param_str = "V16UcV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7099 // __builtin_msa_bnegi_d
7100 .{ .tag = @enumFromInt(964), .properties = .{ .param_str = "V2ULLiV2ULLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7101 // __builtin_msa_bnegi_h
7102 .{ .tag = @enumFromInt(965), .properties = .{ .param_str = "V8UsV8UsIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7103 // __builtin_msa_bnegi_w
7104 .{ .tag = @enumFromInt(966), .properties = .{ .param_str = "V4UiV4UiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7105 // __builtin_msa_bnz_b
7106 .{ .tag = @enumFromInt(967), .properties = .{ .param_str = "iV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7107 // __builtin_msa_bnz_d
7108 .{ .tag = @enumFromInt(968), .properties = .{ .param_str = "iV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7109 // __builtin_msa_bnz_h
7110 .{ .tag = @enumFromInt(969), .properties = .{ .param_str = "iV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7111 // __builtin_msa_bnz_v
7112 .{ .tag = @enumFromInt(970), .properties = .{ .param_str = "iV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7113 // __builtin_msa_bnz_w
7114 .{ .tag = @enumFromInt(971), .properties = .{ .param_str = "iV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7115 // __builtin_msa_bsel_v
7116 .{ .tag = @enumFromInt(972), .properties = .{ .param_str = "V16UcV16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7117 // __builtin_msa_bseli_b
7118 .{ .tag = @enumFromInt(973), .properties = .{ .param_str = "V16UcV16UcV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7119 // __builtin_msa_bset_b
7120 .{ .tag = @enumFromInt(974), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7121 // __builtin_msa_bset_d
7122 .{ .tag = @enumFromInt(975), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7123 // __builtin_msa_bset_h
7124 .{ .tag = @enumFromInt(976), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7125 // __builtin_msa_bset_w
7126 .{ .tag = @enumFromInt(977), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7127 // __builtin_msa_bseti_b
7128 .{ .tag = @enumFromInt(978), .properties = .{ .param_str = "V16UcV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7129 // __builtin_msa_bseti_d
7130 .{ .tag = @enumFromInt(979), .properties = .{ .param_str = "V2ULLiV2ULLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7131 // __builtin_msa_bseti_h
7132 .{ .tag = @enumFromInt(980), .properties = .{ .param_str = "V8UsV8UsIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7133 // __builtin_msa_bseti_w
7134 .{ .tag = @enumFromInt(981), .properties = .{ .param_str = "V4UiV4UiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7135 // __builtin_msa_bz_b
7136 .{ .tag = @enumFromInt(982), .properties = .{ .param_str = "iV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7137 // __builtin_msa_bz_d
7138 .{ .tag = @enumFromInt(983), .properties = .{ .param_str = "iV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7139 // __builtin_msa_bz_h
7140 .{ .tag = @enumFromInt(984), .properties = .{ .param_str = "iV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7141 // __builtin_msa_bz_v
7142 .{ .tag = @enumFromInt(985), .properties = .{ .param_str = "iV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7143 // __builtin_msa_bz_w
7144 .{ .tag = @enumFromInt(986), .properties = .{ .param_str = "iV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7145 // __builtin_msa_ceq_b
7146 .{ .tag = @enumFromInt(987), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7147 // __builtin_msa_ceq_d
7148 .{ .tag = @enumFromInt(988), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7149 // __builtin_msa_ceq_h
7150 .{ .tag = @enumFromInt(989), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7151 // __builtin_msa_ceq_w
7152 .{ .tag = @enumFromInt(990), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7153 // __builtin_msa_ceqi_b
7154 .{ .tag = @enumFromInt(991), .properties = .{ .param_str = "V16ScV16ScISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7155 // __builtin_msa_ceqi_d
7156 .{ .tag = @enumFromInt(992), .properties = .{ .param_str = "V2SLLiV2SLLiISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7157 // __builtin_msa_ceqi_h
7158 .{ .tag = @enumFromInt(993), .properties = .{ .param_str = "V8SsV8SsISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7159 // __builtin_msa_ceqi_w
7160 .{ .tag = @enumFromInt(994), .properties = .{ .param_str = "V4SiV4SiISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7161 // __builtin_msa_cfcmsa
7162 .{ .tag = @enumFromInt(995), .properties = .{ .param_str = "iIi", .target_set = TargetSet.initOne(.mips) } },
7163 // __builtin_msa_cle_s_b
7164 .{ .tag = @enumFromInt(996), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7165 // __builtin_msa_cle_s_d
7166 .{ .tag = @enumFromInt(997), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7167 // __builtin_msa_cle_s_h
7168 .{ .tag = @enumFromInt(998), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7169 // __builtin_msa_cle_s_w
7170 .{ .tag = @enumFromInt(999), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7171 // __builtin_msa_cle_u_b
7172 .{ .tag = @enumFromInt(1000), .properties = .{ .param_str = "V16ScV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7173 // __builtin_msa_cle_u_d
7174 .{ .tag = @enumFromInt(1001), .properties = .{ .param_str = "V2SLLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7175 // __builtin_msa_cle_u_h
7176 .{ .tag = @enumFromInt(1002), .properties = .{ .param_str = "V8SsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7177 // __builtin_msa_cle_u_w
7178 .{ .tag = @enumFromInt(1003), .properties = .{ .param_str = "V4SiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7179 // __builtin_msa_clei_s_b
7180 .{ .tag = @enumFromInt(1004), .properties = .{ .param_str = "V16ScV16ScISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7181 // __builtin_msa_clei_s_d
7182 .{ .tag = @enumFromInt(1005), .properties = .{ .param_str = "V2SLLiV2SLLiISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7183 // __builtin_msa_clei_s_h
7184 .{ .tag = @enumFromInt(1006), .properties = .{ .param_str = "V8SsV8SsISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7185 // __builtin_msa_clei_s_w
7186 .{ .tag = @enumFromInt(1007), .properties = .{ .param_str = "V4SiV4SiISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7187 // __builtin_msa_clei_u_b
7188 .{ .tag = @enumFromInt(1008), .properties = .{ .param_str = "V16ScV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7189 // __builtin_msa_clei_u_d
7190 .{ .tag = @enumFromInt(1009), .properties = .{ .param_str = "V2SLLiV2ULLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7191 // __builtin_msa_clei_u_h
7192 .{ .tag = @enumFromInt(1010), .properties = .{ .param_str = "V8SsV8UsIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7193 // __builtin_msa_clei_u_w
7194 .{ .tag = @enumFromInt(1011), .properties = .{ .param_str = "V4SiV4UiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7195 // __builtin_msa_clt_s_b
7196 .{ .tag = @enumFromInt(1012), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7197 // __builtin_msa_clt_s_d
7198 .{ .tag = @enumFromInt(1013), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7199 // __builtin_msa_clt_s_h
7200 .{ .tag = @enumFromInt(1014), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7201 // __builtin_msa_clt_s_w
7202 .{ .tag = @enumFromInt(1015), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7203 // __builtin_msa_clt_u_b
7204 .{ .tag = @enumFromInt(1016), .properties = .{ .param_str = "V16ScV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7205 // __builtin_msa_clt_u_d
7206 .{ .tag = @enumFromInt(1017), .properties = .{ .param_str = "V2SLLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7207 // __builtin_msa_clt_u_h
7208 .{ .tag = @enumFromInt(1018), .properties = .{ .param_str = "V8SsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7209 // __builtin_msa_clt_u_w
7210 .{ .tag = @enumFromInt(1019), .properties = .{ .param_str = "V4SiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7211 // __builtin_msa_clti_s_b
7212 .{ .tag = @enumFromInt(1020), .properties = .{ .param_str = "V16ScV16ScISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7213 // __builtin_msa_clti_s_d
7214 .{ .tag = @enumFromInt(1021), .properties = .{ .param_str = "V2SLLiV2SLLiISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7215 // __builtin_msa_clti_s_h
7216 .{ .tag = @enumFromInt(1022), .properties = .{ .param_str = "V8SsV8SsISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7217 // __builtin_msa_clti_s_w
7218 .{ .tag = @enumFromInt(1023), .properties = .{ .param_str = "V4SiV4SiISi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7219 // __builtin_msa_clti_u_b
7220 .{ .tag = @enumFromInt(1024), .properties = .{ .param_str = "V16ScV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7221 // __builtin_msa_clti_u_d
7222 .{ .tag = @enumFromInt(1025), .properties = .{ .param_str = "V2SLLiV2ULLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7223 // __builtin_msa_clti_u_h
7224 .{ .tag = @enumFromInt(1026), .properties = .{ .param_str = "V8SsV8UsIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7225 // __builtin_msa_clti_u_w
7226 .{ .tag = @enumFromInt(1027), .properties = .{ .param_str = "V4SiV4UiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7227 // __builtin_msa_copy_s_b
7228 .{ .tag = @enumFromInt(1028), .properties = .{ .param_str = "iV16ScIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7229 // __builtin_msa_copy_s_d
7230 .{ .tag = @enumFromInt(1029), .properties = .{ .param_str = "LLiV2SLLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7231 // __builtin_msa_copy_s_h
7232 .{ .tag = @enumFromInt(1030), .properties = .{ .param_str = "iV8SsIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7233 // __builtin_msa_copy_s_w
7234 .{ .tag = @enumFromInt(1031), .properties = .{ .param_str = "iV4SiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7235 // __builtin_msa_copy_u_b
7236 .{ .tag = @enumFromInt(1032), .properties = .{ .param_str = "iV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7237 // __builtin_msa_copy_u_d
7238 .{ .tag = @enumFromInt(1033), .properties = .{ .param_str = "LLiV2ULLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7239 // __builtin_msa_copy_u_h
7240 .{ .tag = @enumFromInt(1034), .properties = .{ .param_str = "iV8UsIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7241 // __builtin_msa_copy_u_w
7242 .{ .tag = @enumFromInt(1035), .properties = .{ .param_str = "iV4UiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7243 // __builtin_msa_ctcmsa
7244 .{ .tag = @enumFromInt(1036), .properties = .{ .param_str = "vIii", .target_set = TargetSet.initOne(.mips) } },
7245 // __builtin_msa_div_s_b
7246 .{ .tag = @enumFromInt(1037), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7247 // __builtin_msa_div_s_d
7248 .{ .tag = @enumFromInt(1038), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7249 // __builtin_msa_div_s_h
7250 .{ .tag = @enumFromInt(1039), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7251 // __builtin_msa_div_s_w
7252 .{ .tag = @enumFromInt(1040), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7253 // __builtin_msa_div_u_b
7254 .{ .tag = @enumFromInt(1041), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7255 // __builtin_msa_div_u_d
7256 .{ .tag = @enumFromInt(1042), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7257 // __builtin_msa_div_u_h
7258 .{ .tag = @enumFromInt(1043), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7259 // __builtin_msa_div_u_w
7260 .{ .tag = @enumFromInt(1044), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7261 // __builtin_msa_dotp_s_d
7262 .{ .tag = @enumFromInt(1045), .properties = .{ .param_str = "V2SLLiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7263 // __builtin_msa_dotp_s_h
7264 .{ .tag = @enumFromInt(1046), .properties = .{ .param_str = "V8SsV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7265 // __builtin_msa_dotp_s_w
7266 .{ .tag = @enumFromInt(1047), .properties = .{ .param_str = "V4SiV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7267 // __builtin_msa_dotp_u_d
7268 .{ .tag = @enumFromInt(1048), .properties = .{ .param_str = "V2ULLiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7269 // __builtin_msa_dotp_u_h
7270 .{ .tag = @enumFromInt(1049), .properties = .{ .param_str = "V8UsV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7271 // __builtin_msa_dotp_u_w
7272 .{ .tag = @enumFromInt(1050), .properties = .{ .param_str = "V4UiV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7273 // __builtin_msa_dpadd_s_d
7274 .{ .tag = @enumFromInt(1051), .properties = .{ .param_str = "V2SLLiV2SLLiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7275 // __builtin_msa_dpadd_s_h
7276 .{ .tag = @enumFromInt(1052), .properties = .{ .param_str = "V8SsV8SsV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7277 // __builtin_msa_dpadd_s_w
7278 .{ .tag = @enumFromInt(1053), .properties = .{ .param_str = "V4SiV4SiV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7279 // __builtin_msa_dpadd_u_d
7280 .{ .tag = @enumFromInt(1054), .properties = .{ .param_str = "V2ULLiV2ULLiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7281 // __builtin_msa_dpadd_u_h
7282 .{ .tag = @enumFromInt(1055), .properties = .{ .param_str = "V8UsV8UsV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7283 // __builtin_msa_dpadd_u_w
7284 .{ .tag = @enumFromInt(1056), .properties = .{ .param_str = "V4UiV4UiV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7285 // __builtin_msa_dpsub_s_d
7286 .{ .tag = @enumFromInt(1057), .properties = .{ .param_str = "V2SLLiV2SLLiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7287 // __builtin_msa_dpsub_s_h
7288 .{ .tag = @enumFromInt(1058), .properties = .{ .param_str = "V8SsV8SsV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7289 // __builtin_msa_dpsub_s_w
7290 .{ .tag = @enumFromInt(1059), .properties = .{ .param_str = "V4SiV4SiV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7291 // __builtin_msa_dpsub_u_d
7292 .{ .tag = @enumFromInt(1060), .properties = .{ .param_str = "V2ULLiV2ULLiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7293 // __builtin_msa_dpsub_u_h
7294 .{ .tag = @enumFromInt(1061), .properties = .{ .param_str = "V8UsV8UsV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7295 // __builtin_msa_dpsub_u_w
7296 .{ .tag = @enumFromInt(1062), .properties = .{ .param_str = "V4UiV4UiV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7297 // __builtin_msa_fadd_d
7298 .{ .tag = @enumFromInt(1063), .properties = .{ .param_str = "V2dV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7299 // __builtin_msa_fadd_w
7300 .{ .tag = @enumFromInt(1064), .properties = .{ .param_str = "V4fV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7301 // __builtin_msa_fcaf_d
7302 .{ .tag = @enumFromInt(1065), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7303 // __builtin_msa_fcaf_w
7304 .{ .tag = @enumFromInt(1066), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7305 // __builtin_msa_fceq_d
7306 .{ .tag = @enumFromInt(1067), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7307 // __builtin_msa_fceq_w
7308 .{ .tag = @enumFromInt(1068), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7309 // __builtin_msa_fclass_d
7310 .{ .tag = @enumFromInt(1069), .properties = .{ .param_str = "V2LLiV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7311 // __builtin_msa_fclass_w
7312 .{ .tag = @enumFromInt(1070), .properties = .{ .param_str = "V4iV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7313 // __builtin_msa_fcle_d
7314 .{ .tag = @enumFromInt(1071), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7315 // __builtin_msa_fcle_w
7316 .{ .tag = @enumFromInt(1072), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7317 // __builtin_msa_fclt_d
7318 .{ .tag = @enumFromInt(1073), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7319 // __builtin_msa_fclt_w
7320 .{ .tag = @enumFromInt(1074), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7321 // __builtin_msa_fcne_d
7322 .{ .tag = @enumFromInt(1075), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7323 // __builtin_msa_fcne_w
7324 .{ .tag = @enumFromInt(1076), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7325 // __builtin_msa_fcor_d
7326 .{ .tag = @enumFromInt(1077), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7327 // __builtin_msa_fcor_w
7328 .{ .tag = @enumFromInt(1078), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7329 // __builtin_msa_fcueq_d
7330 .{ .tag = @enumFromInt(1079), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7331 // __builtin_msa_fcueq_w
7332 .{ .tag = @enumFromInt(1080), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7333 // __builtin_msa_fcule_d
7334 .{ .tag = @enumFromInt(1081), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7335 // __builtin_msa_fcule_w
7336 .{ .tag = @enumFromInt(1082), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7337 // __builtin_msa_fcult_d
7338 .{ .tag = @enumFromInt(1083), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7339 // __builtin_msa_fcult_w
7340 .{ .tag = @enumFromInt(1084), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7341 // __builtin_msa_fcun_d
7342 .{ .tag = @enumFromInt(1085), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7343 // __builtin_msa_fcun_w
7344 .{ .tag = @enumFromInt(1086), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7345 // __builtin_msa_fcune_d
7346 .{ .tag = @enumFromInt(1087), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7347 // __builtin_msa_fcune_w
7348 .{ .tag = @enumFromInt(1088), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7349 // __builtin_msa_fdiv_d
7350 .{ .tag = @enumFromInt(1089), .properties = .{ .param_str = "V2dV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7351 // __builtin_msa_fdiv_w
7352 .{ .tag = @enumFromInt(1090), .properties = .{ .param_str = "V4fV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7353 // __builtin_msa_fexdo_h
7354 .{ .tag = @enumFromInt(1091), .properties = .{ .param_str = "V8hV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7355 // __builtin_msa_fexdo_w
7356 .{ .tag = @enumFromInt(1092), .properties = .{ .param_str = "V4fV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7357 // __builtin_msa_fexp2_d
7358 .{ .tag = @enumFromInt(1093), .properties = .{ .param_str = "V2dV2dV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7359 // __builtin_msa_fexp2_w
7360 .{ .tag = @enumFromInt(1094), .properties = .{ .param_str = "V4fV4fV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7361 // __builtin_msa_fexupl_d
7362 .{ .tag = @enumFromInt(1095), .properties = .{ .param_str = "V2dV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7363 // __builtin_msa_fexupl_w
7364 .{ .tag = @enumFromInt(1096), .properties = .{ .param_str = "V4fV8h", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7365 // __builtin_msa_fexupr_d
7366 .{ .tag = @enumFromInt(1097), .properties = .{ .param_str = "V2dV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7367 // __builtin_msa_fexupr_w
7368 .{ .tag = @enumFromInt(1098), .properties = .{ .param_str = "V4fV8h", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7369 // __builtin_msa_ffint_s_d
7370 .{ .tag = @enumFromInt(1099), .properties = .{ .param_str = "V2dV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7371 // __builtin_msa_ffint_s_w
7372 .{ .tag = @enumFromInt(1100), .properties = .{ .param_str = "V4fV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7373 // __builtin_msa_ffint_u_d
7374 .{ .tag = @enumFromInt(1101), .properties = .{ .param_str = "V2dV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7375 // __builtin_msa_ffint_u_w
7376 .{ .tag = @enumFromInt(1102), .properties = .{ .param_str = "V4fV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7377 // __builtin_msa_ffql_d
7378 .{ .tag = @enumFromInt(1103), .properties = .{ .param_str = "V2dV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7379 // __builtin_msa_ffql_w
7380 .{ .tag = @enumFromInt(1104), .properties = .{ .param_str = "V4fV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7381 // __builtin_msa_ffqr_d
7382 .{ .tag = @enumFromInt(1105), .properties = .{ .param_str = "V2dV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7383 // __builtin_msa_ffqr_w
7384 .{ .tag = @enumFromInt(1106), .properties = .{ .param_str = "V4fV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7385 // __builtin_msa_fill_b
7386 .{ .tag = @enumFromInt(1107), .properties = .{ .param_str = "V16Sci", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7387 // __builtin_msa_fill_d
7388 .{ .tag = @enumFromInt(1108), .properties = .{ .param_str = "V2SLLiLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7389 // __builtin_msa_fill_h
7390 .{ .tag = @enumFromInt(1109), .properties = .{ .param_str = "V8Ssi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7391 // __builtin_msa_fill_w
7392 .{ .tag = @enumFromInt(1110), .properties = .{ .param_str = "V4Sii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7393 // __builtin_msa_flog2_d
7394 .{ .tag = @enumFromInt(1111), .properties = .{ .param_str = "V2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7395 // __builtin_msa_flog2_w
7396 .{ .tag = @enumFromInt(1112), .properties = .{ .param_str = "V4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7397 // __builtin_msa_fmadd_d
7398 .{ .tag = @enumFromInt(1113), .properties = .{ .param_str = "V2dV2dV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7399 // __builtin_msa_fmadd_w
7400 .{ .tag = @enumFromInt(1114), .properties = .{ .param_str = "V4fV4fV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7401 // __builtin_msa_fmax_a_d
7402 .{ .tag = @enumFromInt(1115), .properties = .{ .param_str = "V2dV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7403 // __builtin_msa_fmax_a_w
7404 .{ .tag = @enumFromInt(1116), .properties = .{ .param_str = "V4fV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7405 // __builtin_msa_fmax_d
7406 .{ .tag = @enumFromInt(1117), .properties = .{ .param_str = "V2dV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7407 // __builtin_msa_fmax_w
7408 .{ .tag = @enumFromInt(1118), .properties = .{ .param_str = "V4fV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7409 // __builtin_msa_fmin_a_d
7410 .{ .tag = @enumFromInt(1119), .properties = .{ .param_str = "V2dV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7411 // __builtin_msa_fmin_a_w
7412 .{ .tag = @enumFromInt(1120), .properties = .{ .param_str = "V4fV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7413 // __builtin_msa_fmin_d
7414 .{ .tag = @enumFromInt(1121), .properties = .{ .param_str = "V2dV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7415 // __builtin_msa_fmin_w
7416 .{ .tag = @enumFromInt(1122), .properties = .{ .param_str = "V4fV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7417 // __builtin_msa_fmsub_d
7418 .{ .tag = @enumFromInt(1123), .properties = .{ .param_str = "V2dV2dV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7419 // __builtin_msa_fmsub_w
7420 .{ .tag = @enumFromInt(1124), .properties = .{ .param_str = "V4fV4fV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7421 // __builtin_msa_fmul_d
7422 .{ .tag = @enumFromInt(1125), .properties = .{ .param_str = "V2dV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7423 // __builtin_msa_fmul_w
7424 .{ .tag = @enumFromInt(1126), .properties = .{ .param_str = "V4fV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7425 // __builtin_msa_frcp_d
7426 .{ .tag = @enumFromInt(1127), .properties = .{ .param_str = "V2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7427 // __builtin_msa_frcp_w
7428 .{ .tag = @enumFromInt(1128), .properties = .{ .param_str = "V4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7429 // __builtin_msa_frint_d
7430 .{ .tag = @enumFromInt(1129), .properties = .{ .param_str = "V2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7431 // __builtin_msa_frint_w
7432 .{ .tag = @enumFromInt(1130), .properties = .{ .param_str = "V4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7433 // __builtin_msa_frsqrt_d
7434 .{ .tag = @enumFromInt(1131), .properties = .{ .param_str = "V2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7435 // __builtin_msa_frsqrt_w
7436 .{ .tag = @enumFromInt(1132), .properties = .{ .param_str = "V4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7437 // __builtin_msa_fsaf_d
7438 .{ .tag = @enumFromInt(1133), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7439 // __builtin_msa_fsaf_w
7440 .{ .tag = @enumFromInt(1134), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7441 // __builtin_msa_fseq_d
7442 .{ .tag = @enumFromInt(1135), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7443 // __builtin_msa_fseq_w
7444 .{ .tag = @enumFromInt(1136), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7445 // __builtin_msa_fsle_d
7446 .{ .tag = @enumFromInt(1137), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7447 // __builtin_msa_fsle_w
7448 .{ .tag = @enumFromInt(1138), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7449 // __builtin_msa_fslt_d
7450 .{ .tag = @enumFromInt(1139), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7451 // __builtin_msa_fslt_w
7452 .{ .tag = @enumFromInt(1140), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7453 // __builtin_msa_fsne_d
7454 .{ .tag = @enumFromInt(1141), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7455 // __builtin_msa_fsne_w
7456 .{ .tag = @enumFromInt(1142), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7457 // __builtin_msa_fsor_d
7458 .{ .tag = @enumFromInt(1143), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7459 // __builtin_msa_fsor_w
7460 .{ .tag = @enumFromInt(1144), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7461 // __builtin_msa_fsqrt_d
7462 .{ .tag = @enumFromInt(1145), .properties = .{ .param_str = "V2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7463 // __builtin_msa_fsqrt_w
7464 .{ .tag = @enumFromInt(1146), .properties = .{ .param_str = "V4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7465 // __builtin_msa_fsub_d
7466 .{ .tag = @enumFromInt(1147), .properties = .{ .param_str = "V2dV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7467 // __builtin_msa_fsub_w
7468 .{ .tag = @enumFromInt(1148), .properties = .{ .param_str = "V4fV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7469 // __builtin_msa_fsueq_d
7470 .{ .tag = @enumFromInt(1149), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7471 // __builtin_msa_fsueq_w
7472 .{ .tag = @enumFromInt(1150), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7473 // __builtin_msa_fsule_d
7474 .{ .tag = @enumFromInt(1151), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7475 // __builtin_msa_fsule_w
7476 .{ .tag = @enumFromInt(1152), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7477 // __builtin_msa_fsult_d
7478 .{ .tag = @enumFromInt(1153), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7479 // __builtin_msa_fsult_w
7480 .{ .tag = @enumFromInt(1154), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7481 // __builtin_msa_fsun_d
7482 .{ .tag = @enumFromInt(1155), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7483 // __builtin_msa_fsun_w
7484 .{ .tag = @enumFromInt(1156), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7485 // __builtin_msa_fsune_d
7486 .{ .tag = @enumFromInt(1157), .properties = .{ .param_str = "V2LLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7487 // __builtin_msa_fsune_w
7488 .{ .tag = @enumFromInt(1158), .properties = .{ .param_str = "V4iV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7489 // __builtin_msa_ftint_s_d
7490 .{ .tag = @enumFromInt(1159), .properties = .{ .param_str = "V2SLLiV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7491 // __builtin_msa_ftint_s_w
7492 .{ .tag = @enumFromInt(1160), .properties = .{ .param_str = "V4SiV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7493 // __builtin_msa_ftint_u_d
7494 .{ .tag = @enumFromInt(1161), .properties = .{ .param_str = "V2ULLiV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7495 // __builtin_msa_ftint_u_w
7496 .{ .tag = @enumFromInt(1162), .properties = .{ .param_str = "V4UiV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7497 // __builtin_msa_ftq_h
7498 .{ .tag = @enumFromInt(1163), .properties = .{ .param_str = "V4UiV4fV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7499 // __builtin_msa_ftq_w
7500 .{ .tag = @enumFromInt(1164), .properties = .{ .param_str = "V2ULLiV2dV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7501 // __builtin_msa_ftrunc_s_d
7502 .{ .tag = @enumFromInt(1165), .properties = .{ .param_str = "V2SLLiV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7503 // __builtin_msa_ftrunc_s_w
7504 .{ .tag = @enumFromInt(1166), .properties = .{ .param_str = "V4SiV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7505 // __builtin_msa_ftrunc_u_d
7506 .{ .tag = @enumFromInt(1167), .properties = .{ .param_str = "V2ULLiV2d", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7507 // __builtin_msa_ftrunc_u_w
7508 .{ .tag = @enumFromInt(1168), .properties = .{ .param_str = "V4UiV4f", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7509 // __builtin_msa_hadd_s_d
7510 .{ .tag = @enumFromInt(1169), .properties = .{ .param_str = "V2SLLiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7511 // __builtin_msa_hadd_s_h
7512 .{ .tag = @enumFromInt(1170), .properties = .{ .param_str = "V8SsV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7513 // __builtin_msa_hadd_s_w
7514 .{ .tag = @enumFromInt(1171), .properties = .{ .param_str = "V4SiV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7515 // __builtin_msa_hadd_u_d
7516 .{ .tag = @enumFromInt(1172), .properties = .{ .param_str = "V2ULLiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7517 // __builtin_msa_hadd_u_h
7518 .{ .tag = @enumFromInt(1173), .properties = .{ .param_str = "V8UsV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7519 // __builtin_msa_hadd_u_w
7520 .{ .tag = @enumFromInt(1174), .properties = .{ .param_str = "V4UiV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7521 // __builtin_msa_hsub_s_d
7522 .{ .tag = @enumFromInt(1175), .properties = .{ .param_str = "V2SLLiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7523 // __builtin_msa_hsub_s_h
7524 .{ .tag = @enumFromInt(1176), .properties = .{ .param_str = "V8SsV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7525 // __builtin_msa_hsub_s_w
7526 .{ .tag = @enumFromInt(1177), .properties = .{ .param_str = "V4SiV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7527 // __builtin_msa_hsub_u_d
7528 .{ .tag = @enumFromInt(1178), .properties = .{ .param_str = "V2ULLiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7529 // __builtin_msa_hsub_u_h
7530 .{ .tag = @enumFromInt(1179), .properties = .{ .param_str = "V8UsV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7531 // __builtin_msa_hsub_u_w
7532 .{ .tag = @enumFromInt(1180), .properties = .{ .param_str = "V4UiV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7533 // __builtin_msa_ilvev_b
7534 .{ .tag = @enumFromInt(1181), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7535 // __builtin_msa_ilvev_d
7536 .{ .tag = @enumFromInt(1182), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7537 // __builtin_msa_ilvev_h
7538 .{ .tag = @enumFromInt(1183), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7539 // __builtin_msa_ilvev_w
7540 .{ .tag = @enumFromInt(1184), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7541 // __builtin_msa_ilvl_b
7542 .{ .tag = @enumFromInt(1185), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7543 // __builtin_msa_ilvl_d
7544 .{ .tag = @enumFromInt(1186), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7545 // __builtin_msa_ilvl_h
7546 .{ .tag = @enumFromInt(1187), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7547 // __builtin_msa_ilvl_w
7548 .{ .tag = @enumFromInt(1188), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7549 // __builtin_msa_ilvod_b
7550 .{ .tag = @enumFromInt(1189), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7551 // __builtin_msa_ilvod_d
7552 .{ .tag = @enumFromInt(1190), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7553 // __builtin_msa_ilvod_h
7554 .{ .tag = @enumFromInt(1191), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7555 // __builtin_msa_ilvod_w
7556 .{ .tag = @enumFromInt(1192), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7557 // __builtin_msa_ilvr_b
7558 .{ .tag = @enumFromInt(1193), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7559 // __builtin_msa_ilvr_d
7560 .{ .tag = @enumFromInt(1194), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7561 // __builtin_msa_ilvr_h
7562 .{ .tag = @enumFromInt(1195), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7563 // __builtin_msa_ilvr_w
7564 .{ .tag = @enumFromInt(1196), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7565 // __builtin_msa_insert_b
7566 .{ .tag = @enumFromInt(1197), .properties = .{ .param_str = "V16ScV16ScIUii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7567 // __builtin_msa_insert_d
7568 .{ .tag = @enumFromInt(1198), .properties = .{ .param_str = "V2SLLiV2SLLiIUiLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7569 // __builtin_msa_insert_h
7570 .{ .tag = @enumFromInt(1199), .properties = .{ .param_str = "V8SsV8SsIUii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7571 // __builtin_msa_insert_w
7572 .{ .tag = @enumFromInt(1200), .properties = .{ .param_str = "V4SiV4SiIUii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7573 // __builtin_msa_insve_b
7574 .{ .tag = @enumFromInt(1201), .properties = .{ .param_str = "V16ScV16ScIUiV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7575 // __builtin_msa_insve_d
7576 .{ .tag = @enumFromInt(1202), .properties = .{ .param_str = "V2SLLiV2SLLiIUiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7577 // __builtin_msa_insve_h
7578 .{ .tag = @enumFromInt(1203), .properties = .{ .param_str = "V8SsV8SsIUiV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7579 // __builtin_msa_insve_w
7580 .{ .tag = @enumFromInt(1204), .properties = .{ .param_str = "V4SiV4SiIUiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7581 // __builtin_msa_ld_b
7582 .{ .tag = @enumFromInt(1205), .properties = .{ .param_str = "V16Scv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7583 // __builtin_msa_ld_d
7584 .{ .tag = @enumFromInt(1206), .properties = .{ .param_str = "V2SLLiv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7585 // __builtin_msa_ld_h
7586 .{ .tag = @enumFromInt(1207), .properties = .{ .param_str = "V8Ssv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7587 // __builtin_msa_ld_w
7588 .{ .tag = @enumFromInt(1208), .properties = .{ .param_str = "V4Siv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7589 // __builtin_msa_ldi_b
7590 .{ .tag = @enumFromInt(1209), .properties = .{ .param_str = "V16cIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7591 // __builtin_msa_ldi_d
7592 .{ .tag = @enumFromInt(1210), .properties = .{ .param_str = "V2LLiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7593 // __builtin_msa_ldi_h
7594 .{ .tag = @enumFromInt(1211), .properties = .{ .param_str = "V8sIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7595 // __builtin_msa_ldi_w
7596 .{ .tag = @enumFromInt(1212), .properties = .{ .param_str = "V4iIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7597 // __builtin_msa_ldr_d
7598 .{ .tag = @enumFromInt(1213), .properties = .{ .param_str = "V2SLLiv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7599 // __builtin_msa_ldr_w
7600 .{ .tag = @enumFromInt(1214), .properties = .{ .param_str = "V4Siv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7601 // __builtin_msa_madd_q_h
7602 .{ .tag = @enumFromInt(1215), .properties = .{ .param_str = "V8SsV8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7603 // __builtin_msa_madd_q_w
7604 .{ .tag = @enumFromInt(1216), .properties = .{ .param_str = "V4SiV4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7605 // __builtin_msa_maddr_q_h
7606 .{ .tag = @enumFromInt(1217), .properties = .{ .param_str = "V8SsV8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7607 // __builtin_msa_maddr_q_w
7608 .{ .tag = @enumFromInt(1218), .properties = .{ .param_str = "V4SiV4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7609 // __builtin_msa_maddv_b
7610 .{ .tag = @enumFromInt(1219), .properties = .{ .param_str = "V16ScV16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7611 // __builtin_msa_maddv_d
7612 .{ .tag = @enumFromInt(1220), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7613 // __builtin_msa_maddv_h
7614 .{ .tag = @enumFromInt(1221), .properties = .{ .param_str = "V8SsV8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7615 // __builtin_msa_maddv_w
7616 .{ .tag = @enumFromInt(1222), .properties = .{ .param_str = "V4SiV4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7617 // __builtin_msa_max_a_b
7618 .{ .tag = @enumFromInt(1223), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7619 // __builtin_msa_max_a_d
7620 .{ .tag = @enumFromInt(1224), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7621 // __builtin_msa_max_a_h
7622 .{ .tag = @enumFromInt(1225), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7623 // __builtin_msa_max_a_w
7624 .{ .tag = @enumFromInt(1226), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7625 // __builtin_msa_max_s_b
7626 .{ .tag = @enumFromInt(1227), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7627 // __builtin_msa_max_s_d
7628 .{ .tag = @enumFromInt(1228), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7629 // __builtin_msa_max_s_h
7630 .{ .tag = @enumFromInt(1229), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7631 // __builtin_msa_max_s_w
7632 .{ .tag = @enumFromInt(1230), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7633 // __builtin_msa_max_u_b
7634 .{ .tag = @enumFromInt(1231), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7635 // __builtin_msa_max_u_d
7636 .{ .tag = @enumFromInt(1232), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7637 // __builtin_msa_max_u_h
7638 .{ .tag = @enumFromInt(1233), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7639 // __builtin_msa_max_u_w
7640 .{ .tag = @enumFromInt(1234), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7641 // __builtin_msa_maxi_s_b
7642 .{ .tag = @enumFromInt(1235), .properties = .{ .param_str = "V16ScV16ScIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7643 // __builtin_msa_maxi_s_d
7644 .{ .tag = @enumFromInt(1236), .properties = .{ .param_str = "V2SLLiV2SLLiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7645 // __builtin_msa_maxi_s_h
7646 .{ .tag = @enumFromInt(1237), .properties = .{ .param_str = "V8SsV8SsIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7647 // __builtin_msa_maxi_s_w
7648 .{ .tag = @enumFromInt(1238), .properties = .{ .param_str = "V4SiV4SiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7649 // __builtin_msa_maxi_u_b
7650 .{ .tag = @enumFromInt(1239), .properties = .{ .param_str = "V16UcV16UcIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7651 // __builtin_msa_maxi_u_d
7652 .{ .tag = @enumFromInt(1240), .properties = .{ .param_str = "V2ULLiV2ULLiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7653 // __builtin_msa_maxi_u_h
7654 .{ .tag = @enumFromInt(1241), .properties = .{ .param_str = "V8UsV8UsIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7655 // __builtin_msa_maxi_u_w
7656 .{ .tag = @enumFromInt(1242), .properties = .{ .param_str = "V4UiV4UiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7657 // __builtin_msa_min_a_b
7658 .{ .tag = @enumFromInt(1243), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7659 // __builtin_msa_min_a_d
7660 .{ .tag = @enumFromInt(1244), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7661 // __builtin_msa_min_a_h
7662 .{ .tag = @enumFromInt(1245), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7663 // __builtin_msa_min_a_w
7664 .{ .tag = @enumFromInt(1246), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7665 // __builtin_msa_min_s_b
7666 .{ .tag = @enumFromInt(1247), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7667 // __builtin_msa_min_s_d
7668 .{ .tag = @enumFromInt(1248), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7669 // __builtin_msa_min_s_h
7670 .{ .tag = @enumFromInt(1249), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7671 // __builtin_msa_min_s_w
7672 .{ .tag = @enumFromInt(1250), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7673 // __builtin_msa_min_u_b
7674 .{ .tag = @enumFromInt(1251), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7675 // __builtin_msa_min_u_d
7676 .{ .tag = @enumFromInt(1252), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7677 // __builtin_msa_min_u_h
7678 .{ .tag = @enumFromInt(1253), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7679 // __builtin_msa_min_u_w
7680 .{ .tag = @enumFromInt(1254), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7681 // __builtin_msa_mini_s_b
7682 .{ .tag = @enumFromInt(1255), .properties = .{ .param_str = "V16ScV16ScIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7683 // __builtin_msa_mini_s_d
7684 .{ .tag = @enumFromInt(1256), .properties = .{ .param_str = "V2SLLiV2SLLiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7685 // __builtin_msa_mini_s_h
7686 .{ .tag = @enumFromInt(1257), .properties = .{ .param_str = "V8SsV8SsIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7687 // __builtin_msa_mini_s_w
7688 .{ .tag = @enumFromInt(1258), .properties = .{ .param_str = "V4SiV4SiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7689 // __builtin_msa_mini_u_b
7690 .{ .tag = @enumFromInt(1259), .properties = .{ .param_str = "V16UcV16UcIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7691 // __builtin_msa_mini_u_d
7692 .{ .tag = @enumFromInt(1260), .properties = .{ .param_str = "V2ULLiV2ULLiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7693 // __builtin_msa_mini_u_h
7694 .{ .tag = @enumFromInt(1261), .properties = .{ .param_str = "V8UsV8UsIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7695 // __builtin_msa_mini_u_w
7696 .{ .tag = @enumFromInt(1262), .properties = .{ .param_str = "V4UiV4UiIi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7697 // __builtin_msa_mod_s_b
7698 .{ .tag = @enumFromInt(1263), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7699 // __builtin_msa_mod_s_d
7700 .{ .tag = @enumFromInt(1264), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7701 // __builtin_msa_mod_s_h
7702 .{ .tag = @enumFromInt(1265), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7703 // __builtin_msa_mod_s_w
7704 .{ .tag = @enumFromInt(1266), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7705 // __builtin_msa_mod_u_b
7706 .{ .tag = @enumFromInt(1267), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7707 // __builtin_msa_mod_u_d
7708 .{ .tag = @enumFromInt(1268), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7709 // __builtin_msa_mod_u_h
7710 .{ .tag = @enumFromInt(1269), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7711 // __builtin_msa_mod_u_w
7712 .{ .tag = @enumFromInt(1270), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7713 // __builtin_msa_move_v
7714 .{ .tag = @enumFromInt(1271), .properties = .{ .param_str = "V16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7715 // __builtin_msa_msub_q_h
7716 .{ .tag = @enumFromInt(1272), .properties = .{ .param_str = "V8SsV8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7717 // __builtin_msa_msub_q_w
7718 .{ .tag = @enumFromInt(1273), .properties = .{ .param_str = "V4SiV4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7719 // __builtin_msa_msubr_q_h
7720 .{ .tag = @enumFromInt(1274), .properties = .{ .param_str = "V8SsV8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7721 // __builtin_msa_msubr_q_w
7722 .{ .tag = @enumFromInt(1275), .properties = .{ .param_str = "V4SiV4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7723 // __builtin_msa_msubv_b
7724 .{ .tag = @enumFromInt(1276), .properties = .{ .param_str = "V16ScV16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7725 // __builtin_msa_msubv_d
7726 .{ .tag = @enumFromInt(1277), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7727 // __builtin_msa_msubv_h
7728 .{ .tag = @enumFromInt(1278), .properties = .{ .param_str = "V8SsV8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7729 // __builtin_msa_msubv_w
7730 .{ .tag = @enumFromInt(1279), .properties = .{ .param_str = "V4SiV4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7731 // __builtin_msa_mul_q_h
7732 .{ .tag = @enumFromInt(1280), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7733 // __builtin_msa_mul_q_w
7734 .{ .tag = @enumFromInt(1281), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7735 // __builtin_msa_mulr_q_h
7736 .{ .tag = @enumFromInt(1282), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7737 // __builtin_msa_mulr_q_w
7738 .{ .tag = @enumFromInt(1283), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7739 // __builtin_msa_mulv_b
7740 .{ .tag = @enumFromInt(1284), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7741 // __builtin_msa_mulv_d
7742 .{ .tag = @enumFromInt(1285), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7743 // __builtin_msa_mulv_h
7744 .{ .tag = @enumFromInt(1286), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7745 // __builtin_msa_mulv_w
7746 .{ .tag = @enumFromInt(1287), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7747 // __builtin_msa_nloc_b
7748 .{ .tag = @enumFromInt(1288), .properties = .{ .param_str = "V16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7749 // __builtin_msa_nloc_d
7750 .{ .tag = @enumFromInt(1289), .properties = .{ .param_str = "V2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7751 // __builtin_msa_nloc_h
7752 .{ .tag = @enumFromInt(1290), .properties = .{ .param_str = "V8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7753 // __builtin_msa_nloc_w
7754 .{ .tag = @enumFromInt(1291), .properties = .{ .param_str = "V4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7755 // __builtin_msa_nlzc_b
7756 .{ .tag = @enumFromInt(1292), .properties = .{ .param_str = "V16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7757 // __builtin_msa_nlzc_d
7758 .{ .tag = @enumFromInt(1293), .properties = .{ .param_str = "V2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7759 // __builtin_msa_nlzc_h
7760 .{ .tag = @enumFromInt(1294), .properties = .{ .param_str = "V8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7761 // __builtin_msa_nlzc_w
7762 .{ .tag = @enumFromInt(1295), .properties = .{ .param_str = "V4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7763 // __builtin_msa_nor_v
7764 .{ .tag = @enumFromInt(1296), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7765 // __builtin_msa_nori_b
7766 .{ .tag = @enumFromInt(1297), .properties = .{ .param_str = "V16UcV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7767 // __builtin_msa_or_v
7768 .{ .tag = @enumFromInt(1298), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7769 // __builtin_msa_ori_b
7770 .{ .tag = @enumFromInt(1299), .properties = .{ .param_str = "V16UcV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7771 // __builtin_msa_pckev_b
7772 .{ .tag = @enumFromInt(1300), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7773 // __builtin_msa_pckev_d
7774 .{ .tag = @enumFromInt(1301), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7775 // __builtin_msa_pckev_h
7776 .{ .tag = @enumFromInt(1302), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7777 // __builtin_msa_pckev_w
7778 .{ .tag = @enumFromInt(1303), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7779 // __builtin_msa_pckod_b
7780 .{ .tag = @enumFromInt(1304), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7781 // __builtin_msa_pckod_d
7782 .{ .tag = @enumFromInt(1305), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7783 // __builtin_msa_pckod_h
7784 .{ .tag = @enumFromInt(1306), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7785 // __builtin_msa_pckod_w
7786 .{ .tag = @enumFromInt(1307), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7787 // __builtin_msa_pcnt_b
7788 .{ .tag = @enumFromInt(1308), .properties = .{ .param_str = "V16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7789 // __builtin_msa_pcnt_d
7790 .{ .tag = @enumFromInt(1309), .properties = .{ .param_str = "V2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7791 // __builtin_msa_pcnt_h
7792 .{ .tag = @enumFromInt(1310), .properties = .{ .param_str = "V8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7793 // __builtin_msa_pcnt_w
7794 .{ .tag = @enumFromInt(1311), .properties = .{ .param_str = "V4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7795 // __builtin_msa_sat_s_b
7796 .{ .tag = @enumFromInt(1312), .properties = .{ .param_str = "V16ScV16ScIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7797 // __builtin_msa_sat_s_d
7798 .{ .tag = @enumFromInt(1313), .properties = .{ .param_str = "V2SLLiV2SLLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7799 // __builtin_msa_sat_s_h
7800 .{ .tag = @enumFromInt(1314), .properties = .{ .param_str = "V8SsV8SsIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7801 // __builtin_msa_sat_s_w
7802 .{ .tag = @enumFromInt(1315), .properties = .{ .param_str = "V4SiV4SiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7803 // __builtin_msa_sat_u_b
7804 .{ .tag = @enumFromInt(1316), .properties = .{ .param_str = "V16UcV16UcIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7805 // __builtin_msa_sat_u_d
7806 .{ .tag = @enumFromInt(1317), .properties = .{ .param_str = "V2ULLiV2ULLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7807 // __builtin_msa_sat_u_h
7808 .{ .tag = @enumFromInt(1318), .properties = .{ .param_str = "V8UsV8UsIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7809 // __builtin_msa_sat_u_w
7810 .{ .tag = @enumFromInt(1319), .properties = .{ .param_str = "V4UiV4UiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7811 // __builtin_msa_shf_b
7812 .{ .tag = @enumFromInt(1320), .properties = .{ .param_str = "V16cV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7813 // __builtin_msa_shf_h
7814 .{ .tag = @enumFromInt(1321), .properties = .{ .param_str = "V8sV8sIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7815 // __builtin_msa_shf_w
7816 .{ .tag = @enumFromInt(1322), .properties = .{ .param_str = "V4iV4iIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7817 // __builtin_msa_sld_b
7818 .{ .tag = @enumFromInt(1323), .properties = .{ .param_str = "V16cV16cV16cUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7819 // __builtin_msa_sld_d
7820 .{ .tag = @enumFromInt(1324), .properties = .{ .param_str = "V2LLiV2LLiV2LLiUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7821 // __builtin_msa_sld_h
7822 .{ .tag = @enumFromInt(1325), .properties = .{ .param_str = "V8sV8sV8sUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7823 // __builtin_msa_sld_w
7824 .{ .tag = @enumFromInt(1326), .properties = .{ .param_str = "V4iV4iV4iUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7825 // __builtin_msa_sldi_b
7826 .{ .tag = @enumFromInt(1327), .properties = .{ .param_str = "V16cV16cV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7827 // __builtin_msa_sldi_d
7828 .{ .tag = @enumFromInt(1328), .properties = .{ .param_str = "V2LLiV2LLiV2LLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7829 // __builtin_msa_sldi_h
7830 .{ .tag = @enumFromInt(1329), .properties = .{ .param_str = "V8sV8sV8sIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7831 // __builtin_msa_sldi_w
7832 .{ .tag = @enumFromInt(1330), .properties = .{ .param_str = "V4iV4iV4iIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7833 // __builtin_msa_sll_b
7834 .{ .tag = @enumFromInt(1331), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7835 // __builtin_msa_sll_d
7836 .{ .tag = @enumFromInt(1332), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7837 // __builtin_msa_sll_h
7838 .{ .tag = @enumFromInt(1333), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7839 // __builtin_msa_sll_w
7840 .{ .tag = @enumFromInt(1334), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7841 // __builtin_msa_slli_b
7842 .{ .tag = @enumFromInt(1335), .properties = .{ .param_str = "V16cV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7843 // __builtin_msa_slli_d
7844 .{ .tag = @enumFromInt(1336), .properties = .{ .param_str = "V2LLiV2LLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7845 // __builtin_msa_slli_h
7846 .{ .tag = @enumFromInt(1337), .properties = .{ .param_str = "V8sV8sIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7847 // __builtin_msa_slli_w
7848 .{ .tag = @enumFromInt(1338), .properties = .{ .param_str = "V4iV4iIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7849 // __builtin_msa_splat_b
7850 .{ .tag = @enumFromInt(1339), .properties = .{ .param_str = "V16cV16cUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7851 // __builtin_msa_splat_d
7852 .{ .tag = @enumFromInt(1340), .properties = .{ .param_str = "V2LLiV2LLiUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7853 // __builtin_msa_splat_h
7854 .{ .tag = @enumFromInt(1341), .properties = .{ .param_str = "V8sV8sUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7855 // __builtin_msa_splat_w
7856 .{ .tag = @enumFromInt(1342), .properties = .{ .param_str = "V4iV4iUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7857 // __builtin_msa_splati_b
7858 .{ .tag = @enumFromInt(1343), .properties = .{ .param_str = "V16cV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7859 // __builtin_msa_splati_d
7860 .{ .tag = @enumFromInt(1344), .properties = .{ .param_str = "V2LLiV2LLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7861 // __builtin_msa_splati_h
7862 .{ .tag = @enumFromInt(1345), .properties = .{ .param_str = "V8sV8sIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7863 // __builtin_msa_splati_w
7864 .{ .tag = @enumFromInt(1346), .properties = .{ .param_str = "V4iV4iIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7865 // __builtin_msa_sra_b
7866 .{ .tag = @enumFromInt(1347), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7867 // __builtin_msa_sra_d
7868 .{ .tag = @enumFromInt(1348), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7869 // __builtin_msa_sra_h
7870 .{ .tag = @enumFromInt(1349), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7871 // __builtin_msa_sra_w
7872 .{ .tag = @enumFromInt(1350), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7873 // __builtin_msa_srai_b
7874 .{ .tag = @enumFromInt(1351), .properties = .{ .param_str = "V16cV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7875 // __builtin_msa_srai_d
7876 .{ .tag = @enumFromInt(1352), .properties = .{ .param_str = "V2LLiV2LLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7877 // __builtin_msa_srai_h
7878 .{ .tag = @enumFromInt(1353), .properties = .{ .param_str = "V8sV8sIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7879 // __builtin_msa_srai_w
7880 .{ .tag = @enumFromInt(1354), .properties = .{ .param_str = "V4iV4iIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7881 // __builtin_msa_srar_b
7882 .{ .tag = @enumFromInt(1355), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7883 // __builtin_msa_srar_d
7884 .{ .tag = @enumFromInt(1356), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7885 // __builtin_msa_srar_h
7886 .{ .tag = @enumFromInt(1357), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7887 // __builtin_msa_srar_w
7888 .{ .tag = @enumFromInt(1358), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7889 // __builtin_msa_srari_b
7890 .{ .tag = @enumFromInt(1359), .properties = .{ .param_str = "V16cV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7891 // __builtin_msa_srari_d
7892 .{ .tag = @enumFromInt(1360), .properties = .{ .param_str = "V2LLiV2LLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7893 // __builtin_msa_srari_h
7894 .{ .tag = @enumFromInt(1361), .properties = .{ .param_str = "V8sV8sIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7895 // __builtin_msa_srari_w
7896 .{ .tag = @enumFromInt(1362), .properties = .{ .param_str = "V4iV4iIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7897 // __builtin_msa_srl_b
7898 .{ .tag = @enumFromInt(1363), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7899 // __builtin_msa_srl_d
7900 .{ .tag = @enumFromInt(1364), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7901 // __builtin_msa_srl_h
7902 .{ .tag = @enumFromInt(1365), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7903 // __builtin_msa_srl_w
7904 .{ .tag = @enumFromInt(1366), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7905 // __builtin_msa_srli_b
7906 .{ .tag = @enumFromInt(1367), .properties = .{ .param_str = "V16cV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7907 // __builtin_msa_srli_d
7908 .{ .tag = @enumFromInt(1368), .properties = .{ .param_str = "V2LLiV2LLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7909 // __builtin_msa_srli_h
7910 .{ .tag = @enumFromInt(1369), .properties = .{ .param_str = "V8sV8sIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7911 // __builtin_msa_srli_w
7912 .{ .tag = @enumFromInt(1370), .properties = .{ .param_str = "V4iV4iIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7913 // __builtin_msa_srlr_b
7914 .{ .tag = @enumFromInt(1371), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7915 // __builtin_msa_srlr_d
7916 .{ .tag = @enumFromInt(1372), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7917 // __builtin_msa_srlr_h
7918 .{ .tag = @enumFromInt(1373), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7919 // __builtin_msa_srlr_w
7920 .{ .tag = @enumFromInt(1374), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7921 // __builtin_msa_srlri_b
7922 .{ .tag = @enumFromInt(1375), .properties = .{ .param_str = "V16cV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7923 // __builtin_msa_srlri_d
7924 .{ .tag = @enumFromInt(1376), .properties = .{ .param_str = "V2LLiV2LLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7925 // __builtin_msa_srlri_h
7926 .{ .tag = @enumFromInt(1377), .properties = .{ .param_str = "V8sV8sIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7927 // __builtin_msa_srlri_w
7928 .{ .tag = @enumFromInt(1378), .properties = .{ .param_str = "V4iV4iIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7929 // __builtin_msa_st_b
7930 .{ .tag = @enumFromInt(1379), .properties = .{ .param_str = "vV16Scv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7931 // __builtin_msa_st_d
7932 .{ .tag = @enumFromInt(1380), .properties = .{ .param_str = "vV2SLLiv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7933 // __builtin_msa_st_h
7934 .{ .tag = @enumFromInt(1381), .properties = .{ .param_str = "vV8Ssv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7935 // __builtin_msa_st_w
7936 .{ .tag = @enumFromInt(1382), .properties = .{ .param_str = "vV4Siv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7937 // __builtin_msa_str_d
7938 .{ .tag = @enumFromInt(1383), .properties = .{ .param_str = "vV2SLLiv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7939 // __builtin_msa_str_w
7940 .{ .tag = @enumFromInt(1384), .properties = .{ .param_str = "vV4Siv*Ii", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7941 // __builtin_msa_subs_s_b
7942 .{ .tag = @enumFromInt(1385), .properties = .{ .param_str = "V16ScV16ScV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7943 // __builtin_msa_subs_s_d
7944 .{ .tag = @enumFromInt(1386), .properties = .{ .param_str = "V2SLLiV2SLLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7945 // __builtin_msa_subs_s_h
7946 .{ .tag = @enumFromInt(1387), .properties = .{ .param_str = "V8SsV8SsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7947 // __builtin_msa_subs_s_w
7948 .{ .tag = @enumFromInt(1388), .properties = .{ .param_str = "V4SiV4SiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7949 // __builtin_msa_subs_u_b
7950 .{ .tag = @enumFromInt(1389), .properties = .{ .param_str = "V16UcV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7951 // __builtin_msa_subs_u_d
7952 .{ .tag = @enumFromInt(1390), .properties = .{ .param_str = "V2ULLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7953 // __builtin_msa_subs_u_h
7954 .{ .tag = @enumFromInt(1391), .properties = .{ .param_str = "V8UsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7955 // __builtin_msa_subs_u_w
7956 .{ .tag = @enumFromInt(1392), .properties = .{ .param_str = "V4UiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7957 // __builtin_msa_subsus_u_b
7958 .{ .tag = @enumFromInt(1393), .properties = .{ .param_str = "V16UcV16UcV16Sc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7959 // __builtin_msa_subsus_u_d
7960 .{ .tag = @enumFromInt(1394), .properties = .{ .param_str = "V2ULLiV2ULLiV2SLLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7961 // __builtin_msa_subsus_u_h
7962 .{ .tag = @enumFromInt(1395), .properties = .{ .param_str = "V8UsV8UsV8Ss", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7963 // __builtin_msa_subsus_u_w
7964 .{ .tag = @enumFromInt(1396), .properties = .{ .param_str = "V4UiV4UiV4Si", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7965 // __builtin_msa_subsuu_s_b
7966 .{ .tag = @enumFromInt(1397), .properties = .{ .param_str = "V16ScV16UcV16Uc", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7967 // __builtin_msa_subsuu_s_d
7968 .{ .tag = @enumFromInt(1398), .properties = .{ .param_str = "V2SLLiV2ULLiV2ULLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7969 // __builtin_msa_subsuu_s_h
7970 .{ .tag = @enumFromInt(1399), .properties = .{ .param_str = "V8SsV8UsV8Us", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7971 // __builtin_msa_subsuu_s_w
7972 .{ .tag = @enumFromInt(1400), .properties = .{ .param_str = "V4SiV4UiV4Ui", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7973 // __builtin_msa_subv_b
7974 .{ .tag = @enumFromInt(1401), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7975 // __builtin_msa_subv_d
7976 .{ .tag = @enumFromInt(1402), .properties = .{ .param_str = "V2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7977 // __builtin_msa_subv_h
7978 .{ .tag = @enumFromInt(1403), .properties = .{ .param_str = "V8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7979 // __builtin_msa_subv_w
7980 .{ .tag = @enumFromInt(1404), .properties = .{ .param_str = "V4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7981 // __builtin_msa_subvi_b
7982 .{ .tag = @enumFromInt(1405), .properties = .{ .param_str = "V16cV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7983 // __builtin_msa_subvi_d
7984 .{ .tag = @enumFromInt(1406), .properties = .{ .param_str = "V2LLiV2LLiIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7985 // __builtin_msa_subvi_h
7986 .{ .tag = @enumFromInt(1407), .properties = .{ .param_str = "V8sV8sIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7987 // __builtin_msa_subvi_w
7988 .{ .tag = @enumFromInt(1408), .properties = .{ .param_str = "V4iV4iIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7989 // __builtin_msa_vshf_b
7990 .{ .tag = @enumFromInt(1409), .properties = .{ .param_str = "V16cV16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7991 // __builtin_msa_vshf_d
7992 .{ .tag = @enumFromInt(1410), .properties = .{ .param_str = "V2LLiV2LLiV2LLiV2LLi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7993 // __builtin_msa_vshf_h
7994 .{ .tag = @enumFromInt(1411), .properties = .{ .param_str = "V8sV8sV8sV8s", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7995 // __builtin_msa_vshf_w
7996 .{ .tag = @enumFromInt(1412), .properties = .{ .param_str = "V4iV4iV4iV4i", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7997 // __builtin_msa_xor_v
7998 .{ .tag = @enumFromInt(1413), .properties = .{ .param_str = "V16cV16cV16c", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
7999 // __builtin_msa_xori_b
8000 .{ .tag = @enumFromInt(1414), .properties = .{ .param_str = "V16cV16cIUi", .target_set = TargetSet.initOne(.mips), .attributes = .{ .@"const" = true } } },
8001 // __builtin_mul_overflow
8002 .{ .tag = @enumFromInt(1415), .properties = .{ .param_str = "b.", .attributes = .{ .custom_typecheck = true, .const_evaluable = true } } },
8003 // __builtin_nan
8004 .{ .tag = @enumFromInt(1416), .properties = .{ .param_str = "dcC*", .attributes = .{ .pure = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8005 // __builtin_nanf
8006 .{ .tag = @enumFromInt(1417), .properties = .{ .param_str = "fcC*", .attributes = .{ .pure = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8007 // __builtin_nanf128
8008 .{ .tag = @enumFromInt(1418), .properties = .{ .param_str = "LLdcC*", .attributes = .{ .pure = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8009 // __builtin_nanf16
8010 .{ .tag = @enumFromInt(1419), .properties = .{ .param_str = "xcC*", .attributes = .{ .pure = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8011 // __builtin_nanl
8012 .{ .tag = @enumFromInt(1420), .properties = .{ .param_str = "LdcC*", .attributes = .{ .pure = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8013 // __builtin_nans
8014 .{ .tag = @enumFromInt(1421), .properties = .{ .param_str = "dcC*", .attributes = .{ .pure = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8015 // __builtin_nansf
8016 .{ .tag = @enumFromInt(1422), .properties = .{ .param_str = "fcC*", .attributes = .{ .pure = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8017 // __builtin_nansf128
8018 .{ .tag = @enumFromInt(1423), .properties = .{ .param_str = "LLdcC*", .attributes = .{ .pure = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8019 // __builtin_nansf16
8020 .{ .tag = @enumFromInt(1424), .properties = .{ .param_str = "xcC*", .attributes = .{ .pure = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8021 // __builtin_nansl
8022 .{ .tag = @enumFromInt(1425), .properties = .{ .param_str = "LdcC*", .attributes = .{ .pure = true, .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8023 // __builtin_nearbyint
8024 .{ .tag = @enumFromInt(1426), .properties = .{ .param_str = "dd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8025 // __builtin_nearbyintf
8026 .{ .tag = @enumFromInt(1427), .properties = .{ .param_str = "ff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8027 // __builtin_nearbyintf128
8028 .{ .tag = @enumFromInt(1428), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8029 // __builtin_nearbyintl
8030 .{ .tag = @enumFromInt(1429), .properties = .{ .param_str = "LdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8031 // __builtin_nextafter
8032 .{ .tag = @enumFromInt(1430), .properties = .{ .param_str = "ddd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8033 // __builtin_nextafterf
8034 .{ .tag = @enumFromInt(1431), .properties = .{ .param_str = "fff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8035 // __builtin_nextafterf128
8036 .{ .tag = @enumFromInt(1432), .properties = .{ .param_str = "LLdLLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8037 // __builtin_nextafterl
8038 .{ .tag = @enumFromInt(1433), .properties = .{ .param_str = "LdLdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8039 // __builtin_nexttoward
8040 .{ .tag = @enumFromInt(1434), .properties = .{ .param_str = "ddLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8041 // __builtin_nexttowardf
8042 .{ .tag = @enumFromInt(1435), .properties = .{ .param_str = "ffLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8043 // __builtin_nexttowardf128
8044 .{ .tag = @enumFromInt(1436), .properties = .{ .param_str = "LLdLLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8045 // __builtin_nexttowardl
8046 .{ .tag = @enumFromInt(1437), .properties = .{ .param_str = "LdLdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8047 // __builtin_nondeterministic_value
8048 .{ .tag = @enumFromInt(1438), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
8049 // __builtin_nontemporal_load
8050 .{ .tag = @enumFromInt(1439), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
8051 // __builtin_nontemporal_store
8052 .{ .tag = @enumFromInt(1440), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
8053 // __builtin_objc_memmove_collectable
8054 .{ .tag = @enumFromInt(1441), .properties = .{ .param_str = "v*v*vC*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8055 // __builtin_object_size
8056 .{ .tag = @enumFromInt(1442), .properties = .{ .param_str = "zvC*i", .attributes = .{ .eval_args = false, .const_evaluable = true } } },
8057 // __builtin_operator_delete
8058 .{ .tag = @enumFromInt(1443), .properties = .{ .param_str = "vv*", .attributes = .{ .custom_typecheck = true, .const_evaluable = true } } },
8059 // __builtin_operator_new
8060 .{ .tag = @enumFromInt(1444), .properties = .{ .param_str = "v*z", .attributes = .{ .@"const" = true, .custom_typecheck = true, .const_evaluable = true } } },
8061 // __builtin_os_log_format
8062 .{ .tag = @enumFromInt(1445), .properties = .{ .param_str = "v*v*cC*.", .attributes = .{ .custom_typecheck = true, .format_kind = .printf } } },
8063 // __builtin_os_log_format_buffer_size
8064 .{ .tag = @enumFromInt(1446), .properties = .{ .param_str = "zcC*.", .attributes = .{ .custom_typecheck = true, .format_kind = .printf, .eval_args = false, .const_evaluable = true } } },
8065 // __builtin_pack_longdouble
8066 .{ .tag = @enumFromInt(1447), .properties = .{ .param_str = "Lddd", .target_set = TargetSet.initOne(.ppc) } },
8067 // __builtin_parity
8068 .{ .tag = @enumFromInt(1448), .properties = .{ .param_str = "iUi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8069 // __builtin_parityl
8070 .{ .tag = @enumFromInt(1449), .properties = .{ .param_str = "iULi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8071 // __builtin_parityll
8072 .{ .tag = @enumFromInt(1450), .properties = .{ .param_str = "iULLi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8073 // __builtin_popcount
8074 .{ .tag = @enumFromInt(1451), .properties = .{ .param_str = "iUi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8075 // __builtin_popcountl
8076 .{ .tag = @enumFromInt(1452), .properties = .{ .param_str = "iULi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8077 // __builtin_popcountll
8078 .{ .tag = @enumFromInt(1453), .properties = .{ .param_str = "iULLi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8079 // __builtin_pow
8080 .{ .tag = @enumFromInt(1454), .properties = .{ .param_str = "ddd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8081 // __builtin_powf
8082 .{ .tag = @enumFromInt(1455), .properties = .{ .param_str = "fff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8083 // __builtin_powf128
8084 .{ .tag = @enumFromInt(1456), .properties = .{ .param_str = "LLdLLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8085 // __builtin_powf16
8086 .{ .tag = @enumFromInt(1457), .properties = .{ .param_str = "hhh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8087 // __builtin_powi
8088 .{ .tag = @enumFromInt(1458), .properties = .{ .param_str = "ddi", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8089 // __builtin_powif
8090 .{ .tag = @enumFromInt(1459), .properties = .{ .param_str = "ffi", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8091 // __builtin_powil
8092 .{ .tag = @enumFromInt(1460), .properties = .{ .param_str = "LdLdi", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8093 // __builtin_powl
8094 .{ .tag = @enumFromInt(1461), .properties = .{ .param_str = "LdLdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8095 // __builtin_ppc_alignx
8096 .{ .tag = @enumFromInt(1462), .properties = .{ .param_str = "vIivC*", .target_set = TargetSet.initOne(.ppc), .attributes = .{ .@"const" = true } } },
8097 // __builtin_ppc_cmpb
8098 .{ .tag = @enumFromInt(1463), .properties = .{ .param_str = "LLiLLiLLi", .target_set = TargetSet.initOne(.ppc) } },
8099 // __builtin_ppc_compare_and_swap
8100 .{ .tag = @enumFromInt(1464), .properties = .{ .param_str = "iiD*i*i", .target_set = TargetSet.initOne(.ppc) } },
8101 // __builtin_ppc_compare_and_swaplp
8102 .{ .tag = @enumFromInt(1465), .properties = .{ .param_str = "iLiD*Li*Li", .target_set = TargetSet.initOne(.ppc) } },
8103 // __builtin_ppc_dcbfl
8104 .{ .tag = @enumFromInt(1466), .properties = .{ .param_str = "vvC*", .target_set = TargetSet.initOne(.ppc) } },
8105 // __builtin_ppc_dcbflp
8106 .{ .tag = @enumFromInt(1467), .properties = .{ .param_str = "vvC*", .target_set = TargetSet.initOne(.ppc) } },
8107 // __builtin_ppc_dcbst
8108 .{ .tag = @enumFromInt(1468), .properties = .{ .param_str = "vvC*", .target_set = TargetSet.initOne(.ppc) } },
8109 // __builtin_ppc_dcbt
8110 .{ .tag = @enumFromInt(1469), .properties = .{ .param_str = "vv*", .target_set = TargetSet.initOne(.ppc) } },
8111 // __builtin_ppc_dcbtst
8112 .{ .tag = @enumFromInt(1470), .properties = .{ .param_str = "vv*", .target_set = TargetSet.initOne(.ppc) } },
8113 // __builtin_ppc_dcbtstt
8114 .{ .tag = @enumFromInt(1471), .properties = .{ .param_str = "vv*", .target_set = TargetSet.initOne(.ppc) } },
8115 // __builtin_ppc_dcbtt
8116 .{ .tag = @enumFromInt(1472), .properties = .{ .param_str = "vv*", .target_set = TargetSet.initOne(.ppc) } },
8117 // __builtin_ppc_dcbz
8118 .{ .tag = @enumFromInt(1473), .properties = .{ .param_str = "vv*", .target_set = TargetSet.initOne(.ppc) } },
8119 // __builtin_ppc_eieio
8120 .{ .tag = @enumFromInt(1474), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.ppc) } },
8121 // __builtin_ppc_fcfid
8122 .{ .tag = @enumFromInt(1475), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8123 // __builtin_ppc_fcfud
8124 .{ .tag = @enumFromInt(1476), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8125 // __builtin_ppc_fctid
8126 .{ .tag = @enumFromInt(1477), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8127 // __builtin_ppc_fctidz
8128 .{ .tag = @enumFromInt(1478), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8129 // __builtin_ppc_fctiw
8130 .{ .tag = @enumFromInt(1479), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8131 // __builtin_ppc_fctiwz
8132 .{ .tag = @enumFromInt(1480), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8133 // __builtin_ppc_fctudz
8134 .{ .tag = @enumFromInt(1481), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8135 // __builtin_ppc_fctuwz
8136 .{ .tag = @enumFromInt(1482), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8137 // __builtin_ppc_fetch_and_add
8138 .{ .tag = @enumFromInt(1483), .properties = .{ .param_str = "iiD*i", .target_set = TargetSet.initOne(.ppc) } },
8139 // __builtin_ppc_fetch_and_addlp
8140 .{ .tag = @enumFromInt(1484), .properties = .{ .param_str = "LiLiD*Li", .target_set = TargetSet.initOne(.ppc) } },
8141 // __builtin_ppc_fetch_and_and
8142 .{ .tag = @enumFromInt(1485), .properties = .{ .param_str = "UiUiD*Ui", .target_set = TargetSet.initOne(.ppc) } },
8143 // __builtin_ppc_fetch_and_andlp
8144 .{ .tag = @enumFromInt(1486), .properties = .{ .param_str = "ULiULiD*ULi", .target_set = TargetSet.initOne(.ppc) } },
8145 // __builtin_ppc_fetch_and_or
8146 .{ .tag = @enumFromInt(1487), .properties = .{ .param_str = "UiUiD*Ui", .target_set = TargetSet.initOne(.ppc) } },
8147 // __builtin_ppc_fetch_and_orlp
8148 .{ .tag = @enumFromInt(1488), .properties = .{ .param_str = "ULiULiD*ULi", .target_set = TargetSet.initOne(.ppc) } },
8149 // __builtin_ppc_fetch_and_swap
8150 .{ .tag = @enumFromInt(1489), .properties = .{ .param_str = "UiUiD*Ui", .target_set = TargetSet.initOne(.ppc) } },
8151 // __builtin_ppc_fetch_and_swaplp
8152 .{ .tag = @enumFromInt(1490), .properties = .{ .param_str = "ULiULiD*ULi", .target_set = TargetSet.initOne(.ppc) } },
8153 // __builtin_ppc_fmsub
8154 .{ .tag = @enumFromInt(1491), .properties = .{ .param_str = "dddd", .target_set = TargetSet.initOne(.ppc) } },
8155 // __builtin_ppc_fmsubs
8156 .{ .tag = @enumFromInt(1492), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.ppc) } },
8157 // __builtin_ppc_fnabs
8158 .{ .tag = @enumFromInt(1493), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8159 // __builtin_ppc_fnabss
8160 .{ .tag = @enumFromInt(1494), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.ppc) } },
8161 // __builtin_ppc_fnmadd
8162 .{ .tag = @enumFromInt(1495), .properties = .{ .param_str = "dddd", .target_set = TargetSet.initOne(.ppc) } },
8163 // __builtin_ppc_fnmadds
8164 .{ .tag = @enumFromInt(1496), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.ppc) } },
8165 // __builtin_ppc_fnmsub
8166 .{ .tag = @enumFromInt(1497), .properties = .{ .param_str = "dddd", .target_set = TargetSet.initOne(.ppc) } },
8167 // __builtin_ppc_fnmsubs
8168 .{ .tag = @enumFromInt(1498), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.ppc) } },
8169 // __builtin_ppc_fre
8170 .{ .tag = @enumFromInt(1499), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8171 // __builtin_ppc_fres
8172 .{ .tag = @enumFromInt(1500), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.ppc) } },
8173 // __builtin_ppc_fric
8174 .{ .tag = @enumFromInt(1501), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8175 // __builtin_ppc_frim
8176 .{ .tag = @enumFromInt(1502), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8177 // __builtin_ppc_frims
8178 .{ .tag = @enumFromInt(1503), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.ppc) } },
8179 // __builtin_ppc_frin
8180 .{ .tag = @enumFromInt(1504), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8181 // __builtin_ppc_frins
8182 .{ .tag = @enumFromInt(1505), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.ppc) } },
8183 // __builtin_ppc_frip
8184 .{ .tag = @enumFromInt(1506), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8185 // __builtin_ppc_frips
8186 .{ .tag = @enumFromInt(1507), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.ppc) } },
8187 // __builtin_ppc_friz
8188 .{ .tag = @enumFromInt(1508), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8189 // __builtin_ppc_frizs
8190 .{ .tag = @enumFromInt(1509), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.ppc) } },
8191 // __builtin_ppc_frsqrte
8192 .{ .tag = @enumFromInt(1510), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8193 // __builtin_ppc_frsqrtes
8194 .{ .tag = @enumFromInt(1511), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.ppc) } },
8195 // __builtin_ppc_fsel
8196 .{ .tag = @enumFromInt(1512), .properties = .{ .param_str = "dddd", .target_set = TargetSet.initOne(.ppc) } },
8197 // __builtin_ppc_fsels
8198 .{ .tag = @enumFromInt(1513), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.ppc) } },
8199 // __builtin_ppc_fsqrt
8200 .{ .tag = @enumFromInt(1514), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8201 // __builtin_ppc_fsqrts
8202 .{ .tag = @enumFromInt(1515), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.ppc) } },
8203 // __builtin_ppc_get_timebase
8204 .{ .tag = @enumFromInt(1516), .properties = .{ .param_str = "ULLi", .target_set = TargetSet.initOne(.ppc) } },
8205 // __builtin_ppc_iospace_eieio
8206 .{ .tag = @enumFromInt(1517), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.ppc) } },
8207 // __builtin_ppc_iospace_lwsync
8208 .{ .tag = @enumFromInt(1518), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.ppc) } },
8209 // __builtin_ppc_iospace_sync
8210 .{ .tag = @enumFromInt(1519), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.ppc) } },
8211 // __builtin_ppc_isync
8212 .{ .tag = @enumFromInt(1520), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.ppc) } },
8213 // __builtin_ppc_ldarx
8214 .{ .tag = @enumFromInt(1521), .properties = .{ .param_str = "LiLiD*", .target_set = TargetSet.initOne(.ppc) } },
8215 // __builtin_ppc_load2r
8216 .{ .tag = @enumFromInt(1522), .properties = .{ .param_str = "UsUs*", .target_set = TargetSet.initOne(.ppc) } },
8217 // __builtin_ppc_load4r
8218 .{ .tag = @enumFromInt(1523), .properties = .{ .param_str = "UiUi*", .target_set = TargetSet.initOne(.ppc) } },
8219 // __builtin_ppc_lwarx
8220 .{ .tag = @enumFromInt(1524), .properties = .{ .param_str = "iiD*", .target_set = TargetSet.initOne(.ppc) } },
8221 // __builtin_ppc_lwsync
8222 .{ .tag = @enumFromInt(1525), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.ppc) } },
8223 // __builtin_ppc_maxfe
8224 .{ .tag = @enumFromInt(1526), .properties = .{ .param_str = "LdLdLdLd.", .target_set = TargetSet.initOne(.ppc), .attributes = .{ .custom_typecheck = true } } },
8225 // __builtin_ppc_maxfl
8226 .{ .tag = @enumFromInt(1527), .properties = .{ .param_str = "dddd.", .target_set = TargetSet.initOne(.ppc), .attributes = .{ .custom_typecheck = true } } },
8227 // __builtin_ppc_maxfs
8228 .{ .tag = @enumFromInt(1528), .properties = .{ .param_str = "ffff.", .target_set = TargetSet.initOne(.ppc), .attributes = .{ .custom_typecheck = true } } },
8229 // __builtin_ppc_mfmsr
8230 .{ .tag = @enumFromInt(1529), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.ppc) } },
8231 // __builtin_ppc_mfspr
8232 .{ .tag = @enumFromInt(1530), .properties = .{ .param_str = "ULiIi", .target_set = TargetSet.initOne(.ppc) } },
8233 // __builtin_ppc_mftbu
8234 .{ .tag = @enumFromInt(1531), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.ppc) } },
8235 // __builtin_ppc_minfe
8236 .{ .tag = @enumFromInt(1532), .properties = .{ .param_str = "LdLdLdLd.", .target_set = TargetSet.initOne(.ppc), .attributes = .{ .custom_typecheck = true } } },
8237 // __builtin_ppc_minfl
8238 .{ .tag = @enumFromInt(1533), .properties = .{ .param_str = "dddd.", .target_set = TargetSet.initOne(.ppc), .attributes = .{ .custom_typecheck = true } } },
8239 // __builtin_ppc_minfs
8240 .{ .tag = @enumFromInt(1534), .properties = .{ .param_str = "ffff.", .target_set = TargetSet.initOne(.ppc), .attributes = .{ .custom_typecheck = true } } },
8241 // __builtin_ppc_mtfsb0
8242 .{ .tag = @enumFromInt(1535), .properties = .{ .param_str = "vUIi", .target_set = TargetSet.initOne(.ppc) } },
8243 // __builtin_ppc_mtfsb1
8244 .{ .tag = @enumFromInt(1536), .properties = .{ .param_str = "vUIi", .target_set = TargetSet.initOne(.ppc) } },
8245 // __builtin_ppc_mtfsf
8246 .{ .tag = @enumFromInt(1537), .properties = .{ .param_str = "vUIiUi", .target_set = TargetSet.initOne(.ppc) } },
8247 // __builtin_ppc_mtfsfi
8248 .{ .tag = @enumFromInt(1538), .properties = .{ .param_str = "vUIiUIi", .target_set = TargetSet.initOne(.ppc) } },
8249 // __builtin_ppc_mtmsr
8250 .{ .tag = @enumFromInt(1539), .properties = .{ .param_str = "vUi", .target_set = TargetSet.initOne(.ppc) } },
8251 // __builtin_ppc_mtspr
8252 .{ .tag = @enumFromInt(1540), .properties = .{ .param_str = "vIiULi", .target_set = TargetSet.initOne(.ppc) } },
8253 // __builtin_ppc_mulhd
8254 .{ .tag = @enumFromInt(1541), .properties = .{ .param_str = "LLiLiLi", .target_set = TargetSet.initOne(.ppc) } },
8255 // __builtin_ppc_mulhdu
8256 .{ .tag = @enumFromInt(1542), .properties = .{ .param_str = "ULLiULiULi", .target_set = TargetSet.initOne(.ppc) } },
8257 // __builtin_ppc_mulhw
8258 .{ .tag = @enumFromInt(1543), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.ppc) } },
8259 // __builtin_ppc_mulhwu
8260 .{ .tag = @enumFromInt(1544), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.ppc) } },
8261 // __builtin_ppc_popcntb
8262 .{ .tag = @enumFromInt(1545), .properties = .{ .param_str = "ULiULi", .target_set = TargetSet.initOne(.ppc) } },
8263 // __builtin_ppc_poppar4
8264 .{ .tag = @enumFromInt(1546), .properties = .{ .param_str = "iUi", .target_set = TargetSet.initOne(.ppc) } },
8265 // __builtin_ppc_poppar8
8266 .{ .tag = @enumFromInt(1547), .properties = .{ .param_str = "iULLi", .target_set = TargetSet.initOne(.ppc) } },
8267 // __builtin_ppc_rdlam
8268 .{ .tag = @enumFromInt(1548), .properties = .{ .param_str = "UWiUWiUWiUWIi", .target_set = TargetSet.initOne(.ppc), .attributes = .{ .@"const" = true } } },
8269 // __builtin_ppc_recipdivd
8270 .{ .tag = @enumFromInt(1549), .properties = .{ .param_str = "V2dV2dV2d", .target_set = TargetSet.initOne(.ppc) } },
8271 // __builtin_ppc_recipdivf
8272 .{ .tag = @enumFromInt(1550), .properties = .{ .param_str = "V4fV4fV4f", .target_set = TargetSet.initOne(.ppc) } },
8273 // __builtin_ppc_rldimi
8274 .{ .tag = @enumFromInt(1551), .properties = .{ .param_str = "ULLiULLiULLiIUiIULLi", .target_set = TargetSet.initOne(.ppc) } },
8275 // __builtin_ppc_rlwimi
8276 .{ .tag = @enumFromInt(1552), .properties = .{ .param_str = "UiUiUiIUiIUi", .target_set = TargetSet.initOne(.ppc) } },
8277 // __builtin_ppc_rlwnm
8278 .{ .tag = @enumFromInt(1553), .properties = .{ .param_str = "UiUiUiIUi", .target_set = TargetSet.initOne(.ppc) } },
8279 // __builtin_ppc_rsqrtd
8280 .{ .tag = @enumFromInt(1554), .properties = .{ .param_str = "V2dV2d", .target_set = TargetSet.initOne(.ppc) } },
8281 // __builtin_ppc_rsqrtf
8282 .{ .tag = @enumFromInt(1555), .properties = .{ .param_str = "V4fV4f", .target_set = TargetSet.initOne(.ppc) } },
8283 // __builtin_ppc_stdcx
8284 .{ .tag = @enumFromInt(1556), .properties = .{ .param_str = "iLiD*Li", .target_set = TargetSet.initOne(.ppc) } },
8285 // __builtin_ppc_stfiw
8286 .{ .tag = @enumFromInt(1557), .properties = .{ .param_str = "viC*d", .target_set = TargetSet.initOne(.ppc) } },
8287 // __builtin_ppc_store2r
8288 .{ .tag = @enumFromInt(1558), .properties = .{ .param_str = "vUiUs*", .target_set = TargetSet.initOne(.ppc) } },
8289 // __builtin_ppc_store4r
8290 .{ .tag = @enumFromInt(1559), .properties = .{ .param_str = "vUiUi*", .target_set = TargetSet.initOne(.ppc) } },
8291 // __builtin_ppc_stwcx
8292 .{ .tag = @enumFromInt(1560), .properties = .{ .param_str = "iiD*i", .target_set = TargetSet.initOne(.ppc) } },
8293 // __builtin_ppc_swdiv
8294 .{ .tag = @enumFromInt(1561), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.ppc) } },
8295 // __builtin_ppc_swdiv_nochk
8296 .{ .tag = @enumFromInt(1562), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.ppc) } },
8297 // __builtin_ppc_swdivs
8298 .{ .tag = @enumFromInt(1563), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.ppc) } },
8299 // __builtin_ppc_swdivs_nochk
8300 .{ .tag = @enumFromInt(1564), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.ppc) } },
8301 // __builtin_ppc_sync
8302 .{ .tag = @enumFromInt(1565), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.ppc) } },
8303 // __builtin_ppc_tdw
8304 .{ .tag = @enumFromInt(1566), .properties = .{ .param_str = "vLLiLLiIUi", .target_set = TargetSet.initOne(.ppc) } },
8305 // __builtin_ppc_trap
8306 .{ .tag = @enumFromInt(1567), .properties = .{ .param_str = "vi", .target_set = TargetSet.initOne(.ppc) } },
8307 // __builtin_ppc_trapd
8308 .{ .tag = @enumFromInt(1568), .properties = .{ .param_str = "vLi", .target_set = TargetSet.initOne(.ppc) } },
8309 // __builtin_ppc_tw
8310 .{ .tag = @enumFromInt(1569), .properties = .{ .param_str = "viiIUi", .target_set = TargetSet.initOne(.ppc) } },
8311 // __builtin_prefetch
8312 .{ .tag = @enumFromInt(1570), .properties = .{ .param_str = "vvC*.", .attributes = .{ .@"const" = true } } },
8313 // __builtin_preserve_access_index
8314 .{ .tag = @enumFromInt(1571), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
8315 // __builtin_printf
8316 .{ .tag = @enumFromInt(1572), .properties = .{ .param_str = "icC*R.", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .printf } } },
8317 // __builtin_ptx_get_image_channel_data_typei_
8318 .{ .tag = @enumFromInt(1573), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.nvptx) } },
8319 // __builtin_ptx_get_image_channel_orderi_
8320 .{ .tag = @enumFromInt(1574), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.nvptx) } },
8321 // __builtin_ptx_get_image_depthi_
8322 .{ .tag = @enumFromInt(1575), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.nvptx) } },
8323 // __builtin_ptx_get_image_heighti_
8324 .{ .tag = @enumFromInt(1576), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.nvptx) } },
8325 // __builtin_ptx_get_image_widthi_
8326 .{ .tag = @enumFromInt(1577), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.nvptx) } },
8327 // __builtin_ptx_read_image2Dff_
8328 .{ .tag = @enumFromInt(1578), .properties = .{ .param_str = "V4fiiff", .target_set = TargetSet.initOne(.nvptx) } },
8329 // __builtin_ptx_read_image2Dfi_
8330 .{ .tag = @enumFromInt(1579), .properties = .{ .param_str = "V4fiiii", .target_set = TargetSet.initOne(.nvptx) } },
8331 // __builtin_ptx_read_image2Dif_
8332 .{ .tag = @enumFromInt(1580), .properties = .{ .param_str = "V4iiiff", .target_set = TargetSet.initOne(.nvptx) } },
8333 // __builtin_ptx_read_image2Dii_
8334 .{ .tag = @enumFromInt(1581), .properties = .{ .param_str = "V4iiiii", .target_set = TargetSet.initOne(.nvptx) } },
8335 // __builtin_ptx_read_image3Dff_
8336 .{ .tag = @enumFromInt(1582), .properties = .{ .param_str = "V4fiiffff", .target_set = TargetSet.initOne(.nvptx) } },
8337 // __builtin_ptx_read_image3Dfi_
8338 .{ .tag = @enumFromInt(1583), .properties = .{ .param_str = "V4fiiiiii", .target_set = TargetSet.initOne(.nvptx) } },
8339 // __builtin_ptx_read_image3Dif_
8340 .{ .tag = @enumFromInt(1584), .properties = .{ .param_str = "V4iiiffff", .target_set = TargetSet.initOne(.nvptx) } },
8341 // __builtin_ptx_read_image3Dii_
8342 .{ .tag = @enumFromInt(1585), .properties = .{ .param_str = "V4iiiiiii", .target_set = TargetSet.initOne(.nvptx) } },
8343 // __builtin_ptx_write_image2Df_
8344 .{ .tag = @enumFromInt(1586), .properties = .{ .param_str = "viiiffff", .target_set = TargetSet.initOne(.nvptx) } },
8345 // __builtin_ptx_write_image2Di_
8346 .{ .tag = @enumFromInt(1587), .properties = .{ .param_str = "viiiiiii", .target_set = TargetSet.initOne(.nvptx) } },
8347 // __builtin_ptx_write_image2Dui_
8348 .{ .tag = @enumFromInt(1588), .properties = .{ .param_str = "viiiUiUiUiUi", .target_set = TargetSet.initOne(.nvptx) } },
8349 // __builtin_r600_implicitarg_ptr
8350 .{ .tag = @enumFromInt(1589), .properties = .{ .param_str = "Uc*7", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
8351 // __builtin_r600_read_tgid_x
8352 .{ .tag = @enumFromInt(1590), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
8353 // __builtin_r600_read_tgid_y
8354 .{ .tag = @enumFromInt(1591), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
8355 // __builtin_r600_read_tgid_z
8356 .{ .tag = @enumFromInt(1592), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
8357 // __builtin_r600_read_tidig_x
8358 .{ .tag = @enumFromInt(1593), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
8359 // __builtin_r600_read_tidig_y
8360 .{ .tag = @enumFromInt(1594), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
8361 // __builtin_r600_read_tidig_z
8362 .{ .tag = @enumFromInt(1595), .properties = .{ .param_str = "Ui", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
8363 // __builtin_r600_recipsqrt_ieee
8364 .{ .tag = @enumFromInt(1596), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
8365 // __builtin_r600_recipsqrt_ieeef
8366 .{ .tag = @enumFromInt(1597), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.amdgpu), .attributes = .{ .@"const" = true } } },
8367 // __builtin_readcyclecounter
8368 .{ .tag = @enumFromInt(1598), .properties = .{ .param_str = "ULLi" } },
8369 // __builtin_readflm
8370 .{ .tag = @enumFromInt(1599), .properties = .{ .param_str = "d", .target_set = TargetSet.initOne(.ppc) } },
8371 // __builtin_realloc
8372 .{ .tag = @enumFromInt(1600), .properties = .{ .param_str = "v*v*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8373 // __builtin_reduce_add
8374 .{ .tag = @enumFromInt(1601), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
8375 // __builtin_reduce_and
8376 .{ .tag = @enumFromInt(1602), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
8377 // __builtin_reduce_max
8378 .{ .tag = @enumFromInt(1603), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
8379 // __builtin_reduce_min
8380 .{ .tag = @enumFromInt(1604), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
8381 // __builtin_reduce_mul
8382 .{ .tag = @enumFromInt(1605), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
8383 // __builtin_reduce_or
8384 .{ .tag = @enumFromInt(1606), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
8385 // __builtin_reduce_xor
8386 .{ .tag = @enumFromInt(1607), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
8387 // __builtin_remainder
8388 .{ .tag = @enumFromInt(1608), .properties = .{ .param_str = "ddd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8389 // __builtin_remainderf
8390 .{ .tag = @enumFromInt(1609), .properties = .{ .param_str = "fff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8391 // __builtin_remainderf128
8392 .{ .tag = @enumFromInt(1610), .properties = .{ .param_str = "LLdLLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8393 // __builtin_remainderl
8394 .{ .tag = @enumFromInt(1611), .properties = .{ .param_str = "LdLdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8395 // __builtin_remquo
8396 .{ .tag = @enumFromInt(1612), .properties = .{ .param_str = "dddi*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8397 // __builtin_remquof
8398 .{ .tag = @enumFromInt(1613), .properties = .{ .param_str = "fffi*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8399 // __builtin_remquof128
8400 .{ .tag = @enumFromInt(1614), .properties = .{ .param_str = "LLdLLdLLdi*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8401 // __builtin_remquol
8402 .{ .tag = @enumFromInt(1615), .properties = .{ .param_str = "LdLdLdi*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8403 // __builtin_return_address
8404 .{ .tag = @enumFromInt(1616), .properties = .{ .param_str = "v*IUi" } },
8405 // __builtin_rindex
8406 .{ .tag = @enumFromInt(1617), .properties = .{ .param_str = "c*cC*i", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8407 // __builtin_rint
8408 .{ .tag = @enumFromInt(1618), .properties = .{ .param_str = "dd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8409 // __builtin_rintf
8410 .{ .tag = @enumFromInt(1619), .properties = .{ .param_str = "ff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8411 // __builtin_rintf128
8412 .{ .tag = @enumFromInt(1620), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8413 // __builtin_rintf16
8414 .{ .tag = @enumFromInt(1621), .properties = .{ .param_str = "hh", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8415 // __builtin_rintl
8416 .{ .tag = @enumFromInt(1622), .properties = .{ .param_str = "LdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8417 // __builtin_rotateleft16
8418 .{ .tag = @enumFromInt(1623), .properties = .{ .param_str = "UsUsUs", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8419 // __builtin_rotateleft32
8420 .{ .tag = @enumFromInt(1624), .properties = .{ .param_str = "UZiUZiUZi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8421 // __builtin_rotateleft64
8422 .{ .tag = @enumFromInt(1625), .properties = .{ .param_str = "UWiUWiUWi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8423 // __builtin_rotateleft8
8424 .{ .tag = @enumFromInt(1626), .properties = .{ .param_str = "UcUcUc", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8425 // __builtin_rotateright16
8426 .{ .tag = @enumFromInt(1627), .properties = .{ .param_str = "UsUsUs", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8427 // __builtin_rotateright32
8428 .{ .tag = @enumFromInt(1628), .properties = .{ .param_str = "UZiUZiUZi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8429 // __builtin_rotateright64
8430 .{ .tag = @enumFromInt(1629), .properties = .{ .param_str = "UWiUWiUWi", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8431 // __builtin_rotateright8
8432 .{ .tag = @enumFromInt(1630), .properties = .{ .param_str = "UcUcUc", .attributes = .{ .@"const" = true, .const_evaluable = true } } },
8433 // __builtin_round
8434 .{ .tag = @enumFromInt(1631), .properties = .{ .param_str = "dd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8435 // __builtin_roundeven
8436 .{ .tag = @enumFromInt(1632), .properties = .{ .param_str = "dd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8437 // __builtin_roundevenf
8438 .{ .tag = @enumFromInt(1633), .properties = .{ .param_str = "ff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8439 // __builtin_roundevenf128
8440 .{ .tag = @enumFromInt(1634), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8441 // __builtin_roundevenf16
8442 .{ .tag = @enumFromInt(1635), .properties = .{ .param_str = "hh", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8443 // __builtin_roundevenl
8444 .{ .tag = @enumFromInt(1636), .properties = .{ .param_str = "LdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8445 // __builtin_roundf
8446 .{ .tag = @enumFromInt(1637), .properties = .{ .param_str = "ff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8447 // __builtin_roundf128
8448 .{ .tag = @enumFromInt(1638), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8449 // __builtin_roundf16
8450 .{ .tag = @enumFromInt(1639), .properties = .{ .param_str = "hh", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8451 // __builtin_roundl
8452 .{ .tag = @enumFromInt(1640), .properties = .{ .param_str = "LdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8453 // __builtin_sadd_overflow
8454 .{ .tag = @enumFromInt(1641), .properties = .{ .param_str = "bSiCSiCSi*", .attributes = .{ .const_evaluable = true } } },
8455 // __builtin_saddl_overflow
8456 .{ .tag = @enumFromInt(1642), .properties = .{ .param_str = "bSLiCSLiCSLi*", .attributes = .{ .const_evaluable = true } } },
8457 // __builtin_saddll_overflow
8458 .{ .tag = @enumFromInt(1643), .properties = .{ .param_str = "bSLLiCSLLiCSLLi*", .attributes = .{ .const_evaluable = true } } },
8459 // __builtin_scalbln
8460 .{ .tag = @enumFromInt(1644), .properties = .{ .param_str = "ddLi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8461 // __builtin_scalblnf
8462 .{ .tag = @enumFromInt(1645), .properties = .{ .param_str = "ffLi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8463 // __builtin_scalblnf128
8464 .{ .tag = @enumFromInt(1646), .properties = .{ .param_str = "LLdLLdLi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8465 // __builtin_scalblnl
8466 .{ .tag = @enumFromInt(1647), .properties = .{ .param_str = "LdLdLi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8467 // __builtin_scalbn
8468 .{ .tag = @enumFromInt(1648), .properties = .{ .param_str = "ddi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8469 // __builtin_scalbnf
8470 .{ .tag = @enumFromInt(1649), .properties = .{ .param_str = "ffi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8471 // __builtin_scalbnf128
8472 .{ .tag = @enumFromInt(1650), .properties = .{ .param_str = "LLdLLdi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8473 // __builtin_scalbnl
8474 .{ .tag = @enumFromInt(1651), .properties = .{ .param_str = "LdLdi", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8475 // __builtin_scanf
8476 .{ .tag = @enumFromInt(1652), .properties = .{ .param_str = "icC*R.", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .scanf } } },
8477 // __builtin_set_flt_rounds
8478 .{ .tag = @enumFromInt(1653), .properties = .{ .param_str = "vi" } },
8479 // __builtin_setflm
8480 .{ .tag = @enumFromInt(1654), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.ppc) } },
8481 // __builtin_setjmp
8482 .{ .tag = @enumFromInt(1655), .properties = .{ .param_str = "iv**", .attributes = .{ .returns_twice = true } } },
8483 // __builtin_setps
8484 .{ .tag = @enumFromInt(1656), .properties = .{ .param_str = "vUiUi", .target_set = TargetSet.initOne(.xcore) } },
8485 // __builtin_setrnd
8486 .{ .tag = @enumFromInt(1657), .properties = .{ .param_str = "di", .target_set = TargetSet.initOne(.ppc) } },
8487 // __builtin_shufflevector
8488 .{ .tag = @enumFromInt(1658), .properties = .{ .param_str = "v.", .attributes = .{ .@"const" = true, .custom_typecheck = true } } },
8489 // __builtin_signbit
8490 .{ .tag = @enumFromInt(1659), .properties = .{ .param_str = "i.", .attributes = .{ .@"const" = true, .custom_typecheck = true, .lib_function_with_builtin_prefix = true } } },
8491 // __builtin_signbitf
8492 .{ .tag = @enumFromInt(1660), .properties = .{ .param_str = "if", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8493 // __builtin_signbitl
8494 .{ .tag = @enumFromInt(1661), .properties = .{ .param_str = "iLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8495 // __builtin_sin
8496 .{ .tag = @enumFromInt(1662), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8497 // __builtin_sinf
8498 .{ .tag = @enumFromInt(1663), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8499 // __builtin_sinf128
8500 .{ .tag = @enumFromInt(1664), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8501 // __builtin_sinf16
8502 .{ .tag = @enumFromInt(1665), .properties = .{ .param_str = "hh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8503 // __builtin_sinh
8504 .{ .tag = @enumFromInt(1666), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8505 // __builtin_sinhf
8506 .{ .tag = @enumFromInt(1667), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8507 // __builtin_sinhf128
8508 .{ .tag = @enumFromInt(1668), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8509 // __builtin_sinhl
8510 .{ .tag = @enumFromInt(1669), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8511 // __builtin_sinl
8512 .{ .tag = @enumFromInt(1670), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8513 // __builtin_smul_overflow
8514 .{ .tag = @enumFromInt(1671), .properties = .{ .param_str = "bSiCSiCSi*", .attributes = .{ .const_evaluable = true } } },
8515 // __builtin_smull_overflow
8516 .{ .tag = @enumFromInt(1672), .properties = .{ .param_str = "bSLiCSLiCSLi*", .attributes = .{ .const_evaluable = true } } },
8517 // __builtin_smulll_overflow
8518 .{ .tag = @enumFromInt(1673), .properties = .{ .param_str = "bSLLiCSLLiCSLLi*", .attributes = .{ .const_evaluable = true } } },
8519 // __builtin_snprintf
8520 .{ .tag = @enumFromInt(1674), .properties = .{ .param_str = "ic*RzcC*R.", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .printf, .format_string_position = 2 } } },
8521 // __builtin_sponentry
8522 .{ .tag = @enumFromInt(1675), .properties = .{ .param_str = "v*", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
8523 // __builtin_sprintf
8524 .{ .tag = @enumFromInt(1676), .properties = .{ .param_str = "ic*RcC*R.", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .printf, .format_string_position = 1 } } },
8525 // __builtin_sqrt
8526 .{ .tag = @enumFromInt(1677), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8527 // __builtin_sqrtf
8528 .{ .tag = @enumFromInt(1678), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8529 // __builtin_sqrtf128
8530 .{ .tag = @enumFromInt(1679), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8531 // __builtin_sqrtf16
8532 .{ .tag = @enumFromInt(1680), .properties = .{ .param_str = "hh", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8533 // __builtin_sqrtl
8534 .{ .tag = @enumFromInt(1681), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8535 // __builtin_sscanf
8536 .{ .tag = @enumFromInt(1682), .properties = .{ .param_str = "icC*RcC*R.", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .scanf, .format_string_position = 1 } } },
8537 // __builtin_ssub_overflow
8538 .{ .tag = @enumFromInt(1683), .properties = .{ .param_str = "bSiCSiCSi*", .attributes = .{ .const_evaluable = true } } },
8539 // __builtin_ssubl_overflow
8540 .{ .tag = @enumFromInt(1684), .properties = .{ .param_str = "bSLiCSLiCSLi*", .attributes = .{ .const_evaluable = true } } },
8541 // __builtin_ssubll_overflow
8542 .{ .tag = @enumFromInt(1685), .properties = .{ .param_str = "bSLLiCSLLiCSLLi*", .attributes = .{ .const_evaluable = true } } },
8543 // __builtin_stdarg_start
8544 .{ .tag = @enumFromInt(1686), .properties = .{ .param_str = "vA.", .attributes = .{ .custom_typecheck = true } } },
8545 // __builtin_stpcpy
8546 .{ .tag = @enumFromInt(1687), .properties = .{ .param_str = "c*c*cC*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8547 // __builtin_stpncpy
8548 .{ .tag = @enumFromInt(1688), .properties = .{ .param_str = "c*c*cC*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8549 // __builtin_strcasecmp
8550 .{ .tag = @enumFromInt(1689), .properties = .{ .param_str = "icC*cC*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8551 // __builtin_strcat
8552 .{ .tag = @enumFromInt(1690), .properties = .{ .param_str = "c*c*cC*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8553 // __builtin_strchr
8554 .{ .tag = @enumFromInt(1691), .properties = .{ .param_str = "c*cC*i", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8555 // __builtin_strcmp
8556 .{ .tag = @enumFromInt(1692), .properties = .{ .param_str = "icC*cC*", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8557 // __builtin_strcpy
8558 .{ .tag = @enumFromInt(1693), .properties = .{ .param_str = "c*c*cC*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8559 // __builtin_strcspn
8560 .{ .tag = @enumFromInt(1694), .properties = .{ .param_str = "zcC*cC*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8561 // __builtin_strdup
8562 .{ .tag = @enumFromInt(1695), .properties = .{ .param_str = "c*cC*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8563 // __builtin_strlen
8564 .{ .tag = @enumFromInt(1696), .properties = .{ .param_str = "zcC*", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8565 // __builtin_strncasecmp
8566 .{ .tag = @enumFromInt(1697), .properties = .{ .param_str = "icC*cC*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8567 // __builtin_strncat
8568 .{ .tag = @enumFromInt(1698), .properties = .{ .param_str = "c*c*cC*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8569 // __builtin_strncmp
8570 .{ .tag = @enumFromInt(1699), .properties = .{ .param_str = "icC*cC*z", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
8571 // __builtin_strncpy
8572 .{ .tag = @enumFromInt(1700), .properties = .{ .param_str = "c*c*cC*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8573 // __builtin_strndup
8574 .{ .tag = @enumFromInt(1701), .properties = .{ .param_str = "c*cC*z", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8575 // __builtin_strpbrk
8576 .{ .tag = @enumFromInt(1702), .properties = .{ .param_str = "c*cC*cC*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8577 // __builtin_strrchr
8578 .{ .tag = @enumFromInt(1703), .properties = .{ .param_str = "c*cC*i", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8579 // __builtin_strspn
8580 .{ .tag = @enumFromInt(1704), .properties = .{ .param_str = "zcC*cC*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8581 // __builtin_strstr
8582 .{ .tag = @enumFromInt(1705), .properties = .{ .param_str = "c*cC*cC*", .attributes = .{ .lib_function_with_builtin_prefix = true } } },
8583 // __builtin_sub_overflow
8584 .{ .tag = @enumFromInt(1706), .properties = .{ .param_str = "b.", .attributes = .{ .custom_typecheck = true, .const_evaluable = true } } },
8585 // __builtin_subc
8586 .{ .tag = @enumFromInt(1707), .properties = .{ .param_str = "UiUiCUiCUiCUi*" } },
8587 // __builtin_subcb
8588 .{ .tag = @enumFromInt(1708), .properties = .{ .param_str = "UcUcCUcCUcCUc*" } },
8589 // __builtin_subcl
8590 .{ .tag = @enumFromInt(1709), .properties = .{ .param_str = "ULiULiCULiCULiCULi*" } },
8591 // __builtin_subcll
8592 .{ .tag = @enumFromInt(1710), .properties = .{ .param_str = "ULLiULLiCULLiCULLiCULLi*" } },
8593 // __builtin_subcs
8594 .{ .tag = @enumFromInt(1711), .properties = .{ .param_str = "UsUsCUsCUsCUs*" } },
8595 // __builtin_tan
8596 .{ .tag = @enumFromInt(1712), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8597 // __builtin_tanf
8598 .{ .tag = @enumFromInt(1713), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8599 // __builtin_tanf128
8600 .{ .tag = @enumFromInt(1714), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8601 // __builtin_tanh
8602 .{ .tag = @enumFromInt(1715), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8603 // __builtin_tanhf
8604 .{ .tag = @enumFromInt(1716), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8605 // __builtin_tanhf128
8606 .{ .tag = @enumFromInt(1717), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8607 // __builtin_tanhl
8608 .{ .tag = @enumFromInt(1718), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8609 // __builtin_tanl
8610 .{ .tag = @enumFromInt(1719), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8611 // __builtin_tgamma
8612 .{ .tag = @enumFromInt(1720), .properties = .{ .param_str = "dd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8613 // __builtin_tgammaf
8614 .{ .tag = @enumFromInt(1721), .properties = .{ .param_str = "ff", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8615 // __builtin_tgammaf128
8616 .{ .tag = @enumFromInt(1722), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8617 // __builtin_tgammal
8618 .{ .tag = @enumFromInt(1723), .properties = .{ .param_str = "LdLd", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
8619 // __builtin_thread_pointer
8620 .{ .tag = @enumFromInt(1724), .properties = .{ .param_str = "v*", .attributes = .{ .@"const" = true } } },
8621 // __builtin_trap
8622 .{ .tag = @enumFromInt(1725), .properties = .{ .param_str = "v", .attributes = .{ .noreturn = true } } },
8623 // __builtin_trunc
8624 .{ .tag = @enumFromInt(1726), .properties = .{ .param_str = "dd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8625 // __builtin_truncf
8626 .{ .tag = @enumFromInt(1727), .properties = .{ .param_str = "ff", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8627 // __builtin_truncf128
8628 .{ .tag = @enumFromInt(1728), .properties = .{ .param_str = "LLdLLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8629 // __builtin_truncf16
8630 .{ .tag = @enumFromInt(1729), .properties = .{ .param_str = "hh", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8631 // __builtin_truncl
8632 .{ .tag = @enumFromInt(1730), .properties = .{ .param_str = "LdLd", .attributes = .{ .@"const" = true, .lib_function_with_builtin_prefix = true } } },
8633 // __builtin_uadd_overflow
8634 .{ .tag = @enumFromInt(1731), .properties = .{ .param_str = "bUiCUiCUi*", .attributes = .{ .const_evaluable = true } } },
8635 // __builtin_uaddl_overflow
8636 .{ .tag = @enumFromInt(1732), .properties = .{ .param_str = "bULiCULiCULi*", .attributes = .{ .const_evaluable = true } } },
8637 // __builtin_uaddll_overflow
8638 .{ .tag = @enumFromInt(1733), .properties = .{ .param_str = "bULLiCULLiCULLi*", .attributes = .{ .const_evaluable = true } } },
8639 // __builtin_umul_overflow
8640 .{ .tag = @enumFromInt(1734), .properties = .{ .param_str = "bUiCUiCUi*", .attributes = .{ .const_evaluable = true } } },
8641 // __builtin_umull_overflow
8642 .{ .tag = @enumFromInt(1735), .properties = .{ .param_str = "bULiCULiCULi*", .attributes = .{ .const_evaluable = true } } },
8643 // __builtin_umulll_overflow
8644 .{ .tag = @enumFromInt(1736), .properties = .{ .param_str = "bULLiCULLiCULLi*", .attributes = .{ .const_evaluable = true } } },
8645 // __builtin_unpack_longdouble
8646 .{ .tag = @enumFromInt(1737), .properties = .{ .param_str = "dLdIi", .target_set = TargetSet.initOne(.ppc) } },
8647 // __builtin_unpredictable
8648 .{ .tag = @enumFromInt(1738), .properties = .{ .param_str = "LiLi", .attributes = .{ .@"const" = true } } },
8649 // __builtin_unreachable
8650 .{ .tag = @enumFromInt(1739), .properties = .{ .param_str = "v", .attributes = .{ .noreturn = true } } },
8651 // __builtin_unwind_init
8652 .{ .tag = @enumFromInt(1740), .properties = .{ .param_str = "v" } },
8653 // __builtin_usub_overflow
8654 .{ .tag = @enumFromInt(1741), .properties = .{ .param_str = "bUiCUiCUi*", .attributes = .{ .const_evaluable = true } } },
8655 // __builtin_usubl_overflow
8656 .{ .tag = @enumFromInt(1742), .properties = .{ .param_str = "bULiCULiCULi*", .attributes = .{ .const_evaluable = true } } },
8657 // __builtin_usubll_overflow
8658 .{ .tag = @enumFromInt(1743), .properties = .{ .param_str = "bULLiCULLiCULLi*", .attributes = .{ .const_evaluable = true } } },
8659 // __builtin_va_copy
8660 .{ .tag = @enumFromInt(1744), .properties = .{ .param_str = "vAA" } },
8661 // __builtin_va_end
8662 .{ .tag = @enumFromInt(1745), .properties = .{ .param_str = "vA" } },
8663 // __builtin_va_start
8664 .{ .tag = @enumFromInt(1746), .properties = .{ .param_str = "vA.", .attributes = .{ .custom_typecheck = true } } },
8665 // __builtin_ve_vl_andm_MMM
8666 .{ .tag = @enumFromInt(1747), .properties = .{ .param_str = "V512bV512bV512b", .target_set = TargetSet.initOne(.vevl_gen) } },
8667 // __builtin_ve_vl_andm_mmm
8668 .{ .tag = @enumFromInt(1748), .properties = .{ .param_str = "V256bV256bV256b", .target_set = TargetSet.initOne(.vevl_gen) } },
8669 // __builtin_ve_vl_eqvm_MMM
8670 .{ .tag = @enumFromInt(1749), .properties = .{ .param_str = "V512bV512bV512b", .target_set = TargetSet.initOne(.vevl_gen) } },
8671 // __builtin_ve_vl_eqvm_mmm
8672 .{ .tag = @enumFromInt(1750), .properties = .{ .param_str = "V256bV256bV256b", .target_set = TargetSet.initOne(.vevl_gen) } },
8673 // __builtin_ve_vl_extract_vm512l
8674 .{ .tag = @enumFromInt(1751), .properties = .{ .param_str = "V256bV512b", .target_set = TargetSet.initOne(.ve) } },
8675 // __builtin_ve_vl_extract_vm512u
8676 .{ .tag = @enumFromInt(1752), .properties = .{ .param_str = "V256bV512b", .target_set = TargetSet.initOne(.ve) } },
8677 // __builtin_ve_vl_fencec_s
8678 .{ .tag = @enumFromInt(1753), .properties = .{ .param_str = "vUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8679 // __builtin_ve_vl_fencei
8680 .{ .tag = @enumFromInt(1754), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.vevl_gen) } },
8681 // __builtin_ve_vl_fencem_s
8682 .{ .tag = @enumFromInt(1755), .properties = .{ .param_str = "vUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8683 // __builtin_ve_vl_fidcr_sss
8684 .{ .tag = @enumFromInt(1756), .properties = .{ .param_str = "LUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8685 // __builtin_ve_vl_insert_vm512l
8686 .{ .tag = @enumFromInt(1757), .properties = .{ .param_str = "V512bV512bV256b", .target_set = TargetSet.initOne(.ve) } },
8687 // __builtin_ve_vl_insert_vm512u
8688 .{ .tag = @enumFromInt(1758), .properties = .{ .param_str = "V512bV512bV256b", .target_set = TargetSet.initOne(.ve) } },
8689 // __builtin_ve_vl_lcr_sss
8690 .{ .tag = @enumFromInt(1759), .properties = .{ .param_str = "LUiLUiLUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8691 // __builtin_ve_vl_lsv_vvss
8692 .{ .tag = @enumFromInt(1760), .properties = .{ .param_str = "V256dV256dUiLUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8693 // __builtin_ve_vl_lvm_MMss
8694 .{ .tag = @enumFromInt(1761), .properties = .{ .param_str = "V512bV512bLUiLUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8695 // __builtin_ve_vl_lvm_mmss
8696 .{ .tag = @enumFromInt(1762), .properties = .{ .param_str = "V256bV256bLUiLUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8697 // __builtin_ve_vl_lvsd_svs
8698 .{ .tag = @enumFromInt(1763), .properties = .{ .param_str = "dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8699 // __builtin_ve_vl_lvsl_svs
8700 .{ .tag = @enumFromInt(1764), .properties = .{ .param_str = "LUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8701 // __builtin_ve_vl_lvss_svs
8702 .{ .tag = @enumFromInt(1765), .properties = .{ .param_str = "fV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8703 // __builtin_ve_vl_lzvm_sml
8704 .{ .tag = @enumFromInt(1766), .properties = .{ .param_str = "LUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8705 // __builtin_ve_vl_negm_MM
8706 .{ .tag = @enumFromInt(1767), .properties = .{ .param_str = "V512bV512b", .target_set = TargetSet.initOne(.vevl_gen) } },
8707 // __builtin_ve_vl_negm_mm
8708 .{ .tag = @enumFromInt(1768), .properties = .{ .param_str = "V256bV256b", .target_set = TargetSet.initOne(.vevl_gen) } },
8709 // __builtin_ve_vl_nndm_MMM
8710 .{ .tag = @enumFromInt(1769), .properties = .{ .param_str = "V512bV512bV512b", .target_set = TargetSet.initOne(.vevl_gen) } },
8711 // __builtin_ve_vl_nndm_mmm
8712 .{ .tag = @enumFromInt(1770), .properties = .{ .param_str = "V256bV256bV256b", .target_set = TargetSet.initOne(.vevl_gen) } },
8713 // __builtin_ve_vl_orm_MMM
8714 .{ .tag = @enumFromInt(1771), .properties = .{ .param_str = "V512bV512bV512b", .target_set = TargetSet.initOne(.vevl_gen) } },
8715 // __builtin_ve_vl_orm_mmm
8716 .{ .tag = @enumFromInt(1772), .properties = .{ .param_str = "V256bV256bV256b", .target_set = TargetSet.initOne(.vevl_gen) } },
8717 // __builtin_ve_vl_pack_f32a
8718 .{ .tag = @enumFromInt(1773), .properties = .{ .param_str = "ULifC*", .target_set = TargetSet.initOne(.ve) } },
8719 // __builtin_ve_vl_pack_f32p
8720 .{ .tag = @enumFromInt(1774), .properties = .{ .param_str = "ULifC*fC*", .target_set = TargetSet.initOne(.ve) } },
8721 // __builtin_ve_vl_pcvm_sml
8722 .{ .tag = @enumFromInt(1775), .properties = .{ .param_str = "LUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8723 // __builtin_ve_vl_pfchv_ssl
8724 .{ .tag = @enumFromInt(1776), .properties = .{ .param_str = "vLivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
8725 // __builtin_ve_vl_pfchvnc_ssl
8726 .{ .tag = @enumFromInt(1777), .properties = .{ .param_str = "vLivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
8727 // __builtin_ve_vl_pvadds_vsvMvl
8728 .{ .tag = @enumFromInt(1778), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8729 // __builtin_ve_vl_pvadds_vsvl
8730 .{ .tag = @enumFromInt(1779), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8731 // __builtin_ve_vl_pvadds_vsvvl
8732 .{ .tag = @enumFromInt(1780), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8733 // __builtin_ve_vl_pvadds_vvvMvl
8734 .{ .tag = @enumFromInt(1781), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8735 // __builtin_ve_vl_pvadds_vvvl
8736 .{ .tag = @enumFromInt(1782), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8737 // __builtin_ve_vl_pvadds_vvvvl
8738 .{ .tag = @enumFromInt(1783), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8739 // __builtin_ve_vl_pvaddu_vsvMvl
8740 .{ .tag = @enumFromInt(1784), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8741 // __builtin_ve_vl_pvaddu_vsvl
8742 .{ .tag = @enumFromInt(1785), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8743 // __builtin_ve_vl_pvaddu_vsvvl
8744 .{ .tag = @enumFromInt(1786), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8745 // __builtin_ve_vl_pvaddu_vvvMvl
8746 .{ .tag = @enumFromInt(1787), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8747 // __builtin_ve_vl_pvaddu_vvvl
8748 .{ .tag = @enumFromInt(1788), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8749 // __builtin_ve_vl_pvaddu_vvvvl
8750 .{ .tag = @enumFromInt(1789), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8751 // __builtin_ve_vl_pvand_vsvMvl
8752 .{ .tag = @enumFromInt(1790), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8753 // __builtin_ve_vl_pvand_vsvl
8754 .{ .tag = @enumFromInt(1791), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8755 // __builtin_ve_vl_pvand_vsvvl
8756 .{ .tag = @enumFromInt(1792), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8757 // __builtin_ve_vl_pvand_vvvMvl
8758 .{ .tag = @enumFromInt(1793), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8759 // __builtin_ve_vl_pvand_vvvl
8760 .{ .tag = @enumFromInt(1794), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8761 // __builtin_ve_vl_pvand_vvvvl
8762 .{ .tag = @enumFromInt(1795), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8763 // __builtin_ve_vl_pvbrd_vsMvl
8764 .{ .tag = @enumFromInt(1796), .properties = .{ .param_str = "V256dLUiV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8765 // __builtin_ve_vl_pvbrd_vsl
8766 .{ .tag = @enumFromInt(1797), .properties = .{ .param_str = "V256dLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8767 // __builtin_ve_vl_pvbrd_vsvl
8768 .{ .tag = @enumFromInt(1798), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8769 // __builtin_ve_vl_pvbrv_vvMvl
8770 .{ .tag = @enumFromInt(1799), .properties = .{ .param_str = "V256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8771 // __builtin_ve_vl_pvbrv_vvl
8772 .{ .tag = @enumFromInt(1800), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8773 // __builtin_ve_vl_pvbrv_vvvl
8774 .{ .tag = @enumFromInt(1801), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8775 // __builtin_ve_vl_pvbrvlo_vvl
8776 .{ .tag = @enumFromInt(1802), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8777 // __builtin_ve_vl_pvbrvlo_vvmvl
8778 .{ .tag = @enumFromInt(1803), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8779 // __builtin_ve_vl_pvbrvlo_vvvl
8780 .{ .tag = @enumFromInt(1804), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8781 // __builtin_ve_vl_pvbrvup_vvl
8782 .{ .tag = @enumFromInt(1805), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8783 // __builtin_ve_vl_pvbrvup_vvmvl
8784 .{ .tag = @enumFromInt(1806), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8785 // __builtin_ve_vl_pvbrvup_vvvl
8786 .{ .tag = @enumFromInt(1807), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8787 // __builtin_ve_vl_pvcmps_vsvMvl
8788 .{ .tag = @enumFromInt(1808), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8789 // __builtin_ve_vl_pvcmps_vsvl
8790 .{ .tag = @enumFromInt(1809), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8791 // __builtin_ve_vl_pvcmps_vsvvl
8792 .{ .tag = @enumFromInt(1810), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8793 // __builtin_ve_vl_pvcmps_vvvMvl
8794 .{ .tag = @enumFromInt(1811), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8795 // __builtin_ve_vl_pvcmps_vvvl
8796 .{ .tag = @enumFromInt(1812), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8797 // __builtin_ve_vl_pvcmps_vvvvl
8798 .{ .tag = @enumFromInt(1813), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8799 // __builtin_ve_vl_pvcmpu_vsvMvl
8800 .{ .tag = @enumFromInt(1814), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8801 // __builtin_ve_vl_pvcmpu_vsvl
8802 .{ .tag = @enumFromInt(1815), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8803 // __builtin_ve_vl_pvcmpu_vsvvl
8804 .{ .tag = @enumFromInt(1816), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8805 // __builtin_ve_vl_pvcmpu_vvvMvl
8806 .{ .tag = @enumFromInt(1817), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8807 // __builtin_ve_vl_pvcmpu_vvvl
8808 .{ .tag = @enumFromInt(1818), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8809 // __builtin_ve_vl_pvcmpu_vvvvl
8810 .{ .tag = @enumFromInt(1819), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8811 // __builtin_ve_vl_pvcvtsw_vvl
8812 .{ .tag = @enumFromInt(1820), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8813 // __builtin_ve_vl_pvcvtsw_vvvl
8814 .{ .tag = @enumFromInt(1821), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8815 // __builtin_ve_vl_pvcvtws_vvMvl
8816 .{ .tag = @enumFromInt(1822), .properties = .{ .param_str = "V256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8817 // __builtin_ve_vl_pvcvtws_vvl
8818 .{ .tag = @enumFromInt(1823), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8819 // __builtin_ve_vl_pvcvtws_vvvl
8820 .{ .tag = @enumFromInt(1824), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8821 // __builtin_ve_vl_pvcvtwsrz_vvMvl
8822 .{ .tag = @enumFromInt(1825), .properties = .{ .param_str = "V256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8823 // __builtin_ve_vl_pvcvtwsrz_vvl
8824 .{ .tag = @enumFromInt(1826), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8825 // __builtin_ve_vl_pvcvtwsrz_vvvl
8826 .{ .tag = @enumFromInt(1827), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8827 // __builtin_ve_vl_pveqv_vsvMvl
8828 .{ .tag = @enumFromInt(1828), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8829 // __builtin_ve_vl_pveqv_vsvl
8830 .{ .tag = @enumFromInt(1829), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8831 // __builtin_ve_vl_pveqv_vsvvl
8832 .{ .tag = @enumFromInt(1830), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8833 // __builtin_ve_vl_pveqv_vvvMvl
8834 .{ .tag = @enumFromInt(1831), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8835 // __builtin_ve_vl_pveqv_vvvl
8836 .{ .tag = @enumFromInt(1832), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8837 // __builtin_ve_vl_pveqv_vvvvl
8838 .{ .tag = @enumFromInt(1833), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8839 // __builtin_ve_vl_pvfadd_vsvMvl
8840 .{ .tag = @enumFromInt(1834), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8841 // __builtin_ve_vl_pvfadd_vsvl
8842 .{ .tag = @enumFromInt(1835), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8843 // __builtin_ve_vl_pvfadd_vsvvl
8844 .{ .tag = @enumFromInt(1836), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8845 // __builtin_ve_vl_pvfadd_vvvMvl
8846 .{ .tag = @enumFromInt(1837), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8847 // __builtin_ve_vl_pvfadd_vvvl
8848 .{ .tag = @enumFromInt(1838), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8849 // __builtin_ve_vl_pvfadd_vvvvl
8850 .{ .tag = @enumFromInt(1839), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8851 // __builtin_ve_vl_pvfcmp_vsvMvl
8852 .{ .tag = @enumFromInt(1840), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8853 // __builtin_ve_vl_pvfcmp_vsvl
8854 .{ .tag = @enumFromInt(1841), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8855 // __builtin_ve_vl_pvfcmp_vsvvl
8856 .{ .tag = @enumFromInt(1842), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8857 // __builtin_ve_vl_pvfcmp_vvvMvl
8858 .{ .tag = @enumFromInt(1843), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8859 // __builtin_ve_vl_pvfcmp_vvvl
8860 .{ .tag = @enumFromInt(1844), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8861 // __builtin_ve_vl_pvfcmp_vvvvl
8862 .{ .tag = @enumFromInt(1845), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8863 // __builtin_ve_vl_pvfmad_vsvvMvl
8864 .{ .tag = @enumFromInt(1846), .properties = .{ .param_str = "V256dLUiV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8865 // __builtin_ve_vl_pvfmad_vsvvl
8866 .{ .tag = @enumFromInt(1847), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8867 // __builtin_ve_vl_pvfmad_vsvvvl
8868 .{ .tag = @enumFromInt(1848), .properties = .{ .param_str = "V256dLUiV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8869 // __builtin_ve_vl_pvfmad_vvsvMvl
8870 .{ .tag = @enumFromInt(1849), .properties = .{ .param_str = "V256dV256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8871 // __builtin_ve_vl_pvfmad_vvsvl
8872 .{ .tag = @enumFromInt(1850), .properties = .{ .param_str = "V256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8873 // __builtin_ve_vl_pvfmad_vvsvvl
8874 .{ .tag = @enumFromInt(1851), .properties = .{ .param_str = "V256dV256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8875 // __builtin_ve_vl_pvfmad_vvvvMvl
8876 .{ .tag = @enumFromInt(1852), .properties = .{ .param_str = "V256dV256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8877 // __builtin_ve_vl_pvfmad_vvvvl
8878 .{ .tag = @enumFromInt(1853), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8879 // __builtin_ve_vl_pvfmad_vvvvvl
8880 .{ .tag = @enumFromInt(1854), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8881 // __builtin_ve_vl_pvfmax_vsvMvl
8882 .{ .tag = @enumFromInt(1855), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8883 // __builtin_ve_vl_pvfmax_vsvl
8884 .{ .tag = @enumFromInt(1856), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8885 // __builtin_ve_vl_pvfmax_vsvvl
8886 .{ .tag = @enumFromInt(1857), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8887 // __builtin_ve_vl_pvfmax_vvvMvl
8888 .{ .tag = @enumFromInt(1858), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8889 // __builtin_ve_vl_pvfmax_vvvl
8890 .{ .tag = @enumFromInt(1859), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8891 // __builtin_ve_vl_pvfmax_vvvvl
8892 .{ .tag = @enumFromInt(1860), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8893 // __builtin_ve_vl_pvfmin_vsvMvl
8894 .{ .tag = @enumFromInt(1861), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8895 // __builtin_ve_vl_pvfmin_vsvl
8896 .{ .tag = @enumFromInt(1862), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8897 // __builtin_ve_vl_pvfmin_vsvvl
8898 .{ .tag = @enumFromInt(1863), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8899 // __builtin_ve_vl_pvfmin_vvvMvl
8900 .{ .tag = @enumFromInt(1864), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8901 // __builtin_ve_vl_pvfmin_vvvl
8902 .{ .tag = @enumFromInt(1865), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8903 // __builtin_ve_vl_pvfmin_vvvvl
8904 .{ .tag = @enumFromInt(1866), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8905 // __builtin_ve_vl_pvfmkaf_Ml
8906 .{ .tag = @enumFromInt(1867), .properties = .{ .param_str = "V512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8907 // __builtin_ve_vl_pvfmkat_Ml
8908 .{ .tag = @enumFromInt(1868), .properties = .{ .param_str = "V512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8909 // __builtin_ve_vl_pvfmkseq_MvMl
8910 .{ .tag = @enumFromInt(1869), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8911 // __builtin_ve_vl_pvfmkseq_Mvl
8912 .{ .tag = @enumFromInt(1870), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8913 // __builtin_ve_vl_pvfmkseqnan_MvMl
8914 .{ .tag = @enumFromInt(1871), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8915 // __builtin_ve_vl_pvfmkseqnan_Mvl
8916 .{ .tag = @enumFromInt(1872), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8917 // __builtin_ve_vl_pvfmksge_MvMl
8918 .{ .tag = @enumFromInt(1873), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8919 // __builtin_ve_vl_pvfmksge_Mvl
8920 .{ .tag = @enumFromInt(1874), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8921 // __builtin_ve_vl_pvfmksgenan_MvMl
8922 .{ .tag = @enumFromInt(1875), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8923 // __builtin_ve_vl_pvfmksgenan_Mvl
8924 .{ .tag = @enumFromInt(1876), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8925 // __builtin_ve_vl_pvfmksgt_MvMl
8926 .{ .tag = @enumFromInt(1877), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8927 // __builtin_ve_vl_pvfmksgt_Mvl
8928 .{ .tag = @enumFromInt(1878), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8929 // __builtin_ve_vl_pvfmksgtnan_MvMl
8930 .{ .tag = @enumFromInt(1879), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8931 // __builtin_ve_vl_pvfmksgtnan_Mvl
8932 .{ .tag = @enumFromInt(1880), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8933 // __builtin_ve_vl_pvfmksle_MvMl
8934 .{ .tag = @enumFromInt(1881), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8935 // __builtin_ve_vl_pvfmksle_Mvl
8936 .{ .tag = @enumFromInt(1882), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8937 // __builtin_ve_vl_pvfmkslenan_MvMl
8938 .{ .tag = @enumFromInt(1883), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8939 // __builtin_ve_vl_pvfmkslenan_Mvl
8940 .{ .tag = @enumFromInt(1884), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8941 // __builtin_ve_vl_pvfmksloeq_mvl
8942 .{ .tag = @enumFromInt(1885), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8943 // __builtin_ve_vl_pvfmksloeq_mvml
8944 .{ .tag = @enumFromInt(1886), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8945 // __builtin_ve_vl_pvfmksloeqnan_mvl
8946 .{ .tag = @enumFromInt(1887), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8947 // __builtin_ve_vl_pvfmksloeqnan_mvml
8948 .{ .tag = @enumFromInt(1888), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8949 // __builtin_ve_vl_pvfmksloge_mvl
8950 .{ .tag = @enumFromInt(1889), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8951 // __builtin_ve_vl_pvfmksloge_mvml
8952 .{ .tag = @enumFromInt(1890), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8953 // __builtin_ve_vl_pvfmkslogenan_mvl
8954 .{ .tag = @enumFromInt(1891), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8955 // __builtin_ve_vl_pvfmkslogenan_mvml
8956 .{ .tag = @enumFromInt(1892), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8957 // __builtin_ve_vl_pvfmkslogt_mvl
8958 .{ .tag = @enumFromInt(1893), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8959 // __builtin_ve_vl_pvfmkslogt_mvml
8960 .{ .tag = @enumFromInt(1894), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8961 // __builtin_ve_vl_pvfmkslogtnan_mvl
8962 .{ .tag = @enumFromInt(1895), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8963 // __builtin_ve_vl_pvfmkslogtnan_mvml
8964 .{ .tag = @enumFromInt(1896), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8965 // __builtin_ve_vl_pvfmkslole_mvl
8966 .{ .tag = @enumFromInt(1897), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8967 // __builtin_ve_vl_pvfmkslole_mvml
8968 .{ .tag = @enumFromInt(1898), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8969 // __builtin_ve_vl_pvfmkslolenan_mvl
8970 .{ .tag = @enumFromInt(1899), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8971 // __builtin_ve_vl_pvfmkslolenan_mvml
8972 .{ .tag = @enumFromInt(1900), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8973 // __builtin_ve_vl_pvfmkslolt_mvl
8974 .{ .tag = @enumFromInt(1901), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8975 // __builtin_ve_vl_pvfmkslolt_mvml
8976 .{ .tag = @enumFromInt(1902), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8977 // __builtin_ve_vl_pvfmksloltnan_mvl
8978 .{ .tag = @enumFromInt(1903), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8979 // __builtin_ve_vl_pvfmksloltnan_mvml
8980 .{ .tag = @enumFromInt(1904), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8981 // __builtin_ve_vl_pvfmkslonan_mvl
8982 .{ .tag = @enumFromInt(1905), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8983 // __builtin_ve_vl_pvfmkslonan_mvml
8984 .{ .tag = @enumFromInt(1906), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8985 // __builtin_ve_vl_pvfmkslone_mvl
8986 .{ .tag = @enumFromInt(1907), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8987 // __builtin_ve_vl_pvfmkslone_mvml
8988 .{ .tag = @enumFromInt(1908), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8989 // __builtin_ve_vl_pvfmkslonenan_mvl
8990 .{ .tag = @enumFromInt(1909), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8991 // __builtin_ve_vl_pvfmkslonenan_mvml
8992 .{ .tag = @enumFromInt(1910), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8993 // __builtin_ve_vl_pvfmkslonum_mvl
8994 .{ .tag = @enumFromInt(1911), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8995 // __builtin_ve_vl_pvfmkslonum_mvml
8996 .{ .tag = @enumFromInt(1912), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8997 // __builtin_ve_vl_pvfmkslt_MvMl
8998 .{ .tag = @enumFromInt(1913), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
8999 // __builtin_ve_vl_pvfmkslt_Mvl
9000 .{ .tag = @enumFromInt(1914), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9001 // __builtin_ve_vl_pvfmksltnan_MvMl
9002 .{ .tag = @enumFromInt(1915), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9003 // __builtin_ve_vl_pvfmksltnan_Mvl
9004 .{ .tag = @enumFromInt(1916), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9005 // __builtin_ve_vl_pvfmksnan_MvMl
9006 .{ .tag = @enumFromInt(1917), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9007 // __builtin_ve_vl_pvfmksnan_Mvl
9008 .{ .tag = @enumFromInt(1918), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9009 // __builtin_ve_vl_pvfmksne_MvMl
9010 .{ .tag = @enumFromInt(1919), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9011 // __builtin_ve_vl_pvfmksne_Mvl
9012 .{ .tag = @enumFromInt(1920), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9013 // __builtin_ve_vl_pvfmksnenan_MvMl
9014 .{ .tag = @enumFromInt(1921), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9015 // __builtin_ve_vl_pvfmksnenan_Mvl
9016 .{ .tag = @enumFromInt(1922), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9017 // __builtin_ve_vl_pvfmksnum_MvMl
9018 .{ .tag = @enumFromInt(1923), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9019 // __builtin_ve_vl_pvfmksnum_Mvl
9020 .{ .tag = @enumFromInt(1924), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9021 // __builtin_ve_vl_pvfmksupeq_mvl
9022 .{ .tag = @enumFromInt(1925), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9023 // __builtin_ve_vl_pvfmksupeq_mvml
9024 .{ .tag = @enumFromInt(1926), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9025 // __builtin_ve_vl_pvfmksupeqnan_mvl
9026 .{ .tag = @enumFromInt(1927), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9027 // __builtin_ve_vl_pvfmksupeqnan_mvml
9028 .{ .tag = @enumFromInt(1928), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9029 // __builtin_ve_vl_pvfmksupge_mvl
9030 .{ .tag = @enumFromInt(1929), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9031 // __builtin_ve_vl_pvfmksupge_mvml
9032 .{ .tag = @enumFromInt(1930), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9033 // __builtin_ve_vl_pvfmksupgenan_mvl
9034 .{ .tag = @enumFromInt(1931), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9035 // __builtin_ve_vl_pvfmksupgenan_mvml
9036 .{ .tag = @enumFromInt(1932), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9037 // __builtin_ve_vl_pvfmksupgt_mvl
9038 .{ .tag = @enumFromInt(1933), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9039 // __builtin_ve_vl_pvfmksupgt_mvml
9040 .{ .tag = @enumFromInt(1934), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9041 // __builtin_ve_vl_pvfmksupgtnan_mvl
9042 .{ .tag = @enumFromInt(1935), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9043 // __builtin_ve_vl_pvfmksupgtnan_mvml
9044 .{ .tag = @enumFromInt(1936), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9045 // __builtin_ve_vl_pvfmksuple_mvl
9046 .{ .tag = @enumFromInt(1937), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9047 // __builtin_ve_vl_pvfmksuple_mvml
9048 .{ .tag = @enumFromInt(1938), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9049 // __builtin_ve_vl_pvfmksuplenan_mvl
9050 .{ .tag = @enumFromInt(1939), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9051 // __builtin_ve_vl_pvfmksuplenan_mvml
9052 .{ .tag = @enumFromInt(1940), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9053 // __builtin_ve_vl_pvfmksuplt_mvl
9054 .{ .tag = @enumFromInt(1941), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9055 // __builtin_ve_vl_pvfmksuplt_mvml
9056 .{ .tag = @enumFromInt(1942), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9057 // __builtin_ve_vl_pvfmksupltnan_mvl
9058 .{ .tag = @enumFromInt(1943), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9059 // __builtin_ve_vl_pvfmksupltnan_mvml
9060 .{ .tag = @enumFromInt(1944), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9061 // __builtin_ve_vl_pvfmksupnan_mvl
9062 .{ .tag = @enumFromInt(1945), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9063 // __builtin_ve_vl_pvfmksupnan_mvml
9064 .{ .tag = @enumFromInt(1946), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9065 // __builtin_ve_vl_pvfmksupne_mvl
9066 .{ .tag = @enumFromInt(1947), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9067 // __builtin_ve_vl_pvfmksupne_mvml
9068 .{ .tag = @enumFromInt(1948), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9069 // __builtin_ve_vl_pvfmksupnenan_mvl
9070 .{ .tag = @enumFromInt(1949), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9071 // __builtin_ve_vl_pvfmksupnenan_mvml
9072 .{ .tag = @enumFromInt(1950), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9073 // __builtin_ve_vl_pvfmksupnum_mvl
9074 .{ .tag = @enumFromInt(1951), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9075 // __builtin_ve_vl_pvfmksupnum_mvml
9076 .{ .tag = @enumFromInt(1952), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9077 // __builtin_ve_vl_pvfmkweq_MvMl
9078 .{ .tag = @enumFromInt(1953), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9079 // __builtin_ve_vl_pvfmkweq_Mvl
9080 .{ .tag = @enumFromInt(1954), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9081 // __builtin_ve_vl_pvfmkweqnan_MvMl
9082 .{ .tag = @enumFromInt(1955), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9083 // __builtin_ve_vl_pvfmkweqnan_Mvl
9084 .{ .tag = @enumFromInt(1956), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9085 // __builtin_ve_vl_pvfmkwge_MvMl
9086 .{ .tag = @enumFromInt(1957), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9087 // __builtin_ve_vl_pvfmkwge_Mvl
9088 .{ .tag = @enumFromInt(1958), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9089 // __builtin_ve_vl_pvfmkwgenan_MvMl
9090 .{ .tag = @enumFromInt(1959), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9091 // __builtin_ve_vl_pvfmkwgenan_Mvl
9092 .{ .tag = @enumFromInt(1960), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9093 // __builtin_ve_vl_pvfmkwgt_MvMl
9094 .{ .tag = @enumFromInt(1961), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9095 // __builtin_ve_vl_pvfmkwgt_Mvl
9096 .{ .tag = @enumFromInt(1962), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9097 // __builtin_ve_vl_pvfmkwgtnan_MvMl
9098 .{ .tag = @enumFromInt(1963), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9099 // __builtin_ve_vl_pvfmkwgtnan_Mvl
9100 .{ .tag = @enumFromInt(1964), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9101 // __builtin_ve_vl_pvfmkwle_MvMl
9102 .{ .tag = @enumFromInt(1965), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9103 // __builtin_ve_vl_pvfmkwle_Mvl
9104 .{ .tag = @enumFromInt(1966), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9105 // __builtin_ve_vl_pvfmkwlenan_MvMl
9106 .{ .tag = @enumFromInt(1967), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9107 // __builtin_ve_vl_pvfmkwlenan_Mvl
9108 .{ .tag = @enumFromInt(1968), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9109 // __builtin_ve_vl_pvfmkwloeq_mvl
9110 .{ .tag = @enumFromInt(1969), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9111 // __builtin_ve_vl_pvfmkwloeq_mvml
9112 .{ .tag = @enumFromInt(1970), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9113 // __builtin_ve_vl_pvfmkwloeqnan_mvl
9114 .{ .tag = @enumFromInt(1971), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9115 // __builtin_ve_vl_pvfmkwloeqnan_mvml
9116 .{ .tag = @enumFromInt(1972), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9117 // __builtin_ve_vl_pvfmkwloge_mvl
9118 .{ .tag = @enumFromInt(1973), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9119 // __builtin_ve_vl_pvfmkwloge_mvml
9120 .{ .tag = @enumFromInt(1974), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9121 // __builtin_ve_vl_pvfmkwlogenan_mvl
9122 .{ .tag = @enumFromInt(1975), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9123 // __builtin_ve_vl_pvfmkwlogenan_mvml
9124 .{ .tag = @enumFromInt(1976), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9125 // __builtin_ve_vl_pvfmkwlogt_mvl
9126 .{ .tag = @enumFromInt(1977), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9127 // __builtin_ve_vl_pvfmkwlogt_mvml
9128 .{ .tag = @enumFromInt(1978), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9129 // __builtin_ve_vl_pvfmkwlogtnan_mvl
9130 .{ .tag = @enumFromInt(1979), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9131 // __builtin_ve_vl_pvfmkwlogtnan_mvml
9132 .{ .tag = @enumFromInt(1980), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9133 // __builtin_ve_vl_pvfmkwlole_mvl
9134 .{ .tag = @enumFromInt(1981), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9135 // __builtin_ve_vl_pvfmkwlole_mvml
9136 .{ .tag = @enumFromInt(1982), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9137 // __builtin_ve_vl_pvfmkwlolenan_mvl
9138 .{ .tag = @enumFromInt(1983), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9139 // __builtin_ve_vl_pvfmkwlolenan_mvml
9140 .{ .tag = @enumFromInt(1984), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9141 // __builtin_ve_vl_pvfmkwlolt_mvl
9142 .{ .tag = @enumFromInt(1985), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9143 // __builtin_ve_vl_pvfmkwlolt_mvml
9144 .{ .tag = @enumFromInt(1986), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9145 // __builtin_ve_vl_pvfmkwloltnan_mvl
9146 .{ .tag = @enumFromInt(1987), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9147 // __builtin_ve_vl_pvfmkwloltnan_mvml
9148 .{ .tag = @enumFromInt(1988), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9149 // __builtin_ve_vl_pvfmkwlonan_mvl
9150 .{ .tag = @enumFromInt(1989), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9151 // __builtin_ve_vl_pvfmkwlonan_mvml
9152 .{ .tag = @enumFromInt(1990), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9153 // __builtin_ve_vl_pvfmkwlone_mvl
9154 .{ .tag = @enumFromInt(1991), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9155 // __builtin_ve_vl_pvfmkwlone_mvml
9156 .{ .tag = @enumFromInt(1992), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9157 // __builtin_ve_vl_pvfmkwlonenan_mvl
9158 .{ .tag = @enumFromInt(1993), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9159 // __builtin_ve_vl_pvfmkwlonenan_mvml
9160 .{ .tag = @enumFromInt(1994), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9161 // __builtin_ve_vl_pvfmkwlonum_mvl
9162 .{ .tag = @enumFromInt(1995), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9163 // __builtin_ve_vl_pvfmkwlonum_mvml
9164 .{ .tag = @enumFromInt(1996), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9165 // __builtin_ve_vl_pvfmkwlt_MvMl
9166 .{ .tag = @enumFromInt(1997), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9167 // __builtin_ve_vl_pvfmkwlt_Mvl
9168 .{ .tag = @enumFromInt(1998), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9169 // __builtin_ve_vl_pvfmkwltnan_MvMl
9170 .{ .tag = @enumFromInt(1999), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9171 // __builtin_ve_vl_pvfmkwltnan_Mvl
9172 .{ .tag = @enumFromInt(2000), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9173 // __builtin_ve_vl_pvfmkwnan_MvMl
9174 .{ .tag = @enumFromInt(2001), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9175 // __builtin_ve_vl_pvfmkwnan_Mvl
9176 .{ .tag = @enumFromInt(2002), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9177 // __builtin_ve_vl_pvfmkwne_MvMl
9178 .{ .tag = @enumFromInt(2003), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9179 // __builtin_ve_vl_pvfmkwne_Mvl
9180 .{ .tag = @enumFromInt(2004), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9181 // __builtin_ve_vl_pvfmkwnenan_MvMl
9182 .{ .tag = @enumFromInt(2005), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9183 // __builtin_ve_vl_pvfmkwnenan_Mvl
9184 .{ .tag = @enumFromInt(2006), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9185 // __builtin_ve_vl_pvfmkwnum_MvMl
9186 .{ .tag = @enumFromInt(2007), .properties = .{ .param_str = "V512bV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9187 // __builtin_ve_vl_pvfmkwnum_Mvl
9188 .{ .tag = @enumFromInt(2008), .properties = .{ .param_str = "V512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9189 // __builtin_ve_vl_pvfmkwupeq_mvl
9190 .{ .tag = @enumFromInt(2009), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9191 // __builtin_ve_vl_pvfmkwupeq_mvml
9192 .{ .tag = @enumFromInt(2010), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9193 // __builtin_ve_vl_pvfmkwupeqnan_mvl
9194 .{ .tag = @enumFromInt(2011), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9195 // __builtin_ve_vl_pvfmkwupeqnan_mvml
9196 .{ .tag = @enumFromInt(2012), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9197 // __builtin_ve_vl_pvfmkwupge_mvl
9198 .{ .tag = @enumFromInt(2013), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9199 // __builtin_ve_vl_pvfmkwupge_mvml
9200 .{ .tag = @enumFromInt(2014), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9201 // __builtin_ve_vl_pvfmkwupgenan_mvl
9202 .{ .tag = @enumFromInt(2015), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9203 // __builtin_ve_vl_pvfmkwupgenan_mvml
9204 .{ .tag = @enumFromInt(2016), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9205 // __builtin_ve_vl_pvfmkwupgt_mvl
9206 .{ .tag = @enumFromInt(2017), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9207 // __builtin_ve_vl_pvfmkwupgt_mvml
9208 .{ .tag = @enumFromInt(2018), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9209 // __builtin_ve_vl_pvfmkwupgtnan_mvl
9210 .{ .tag = @enumFromInt(2019), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9211 // __builtin_ve_vl_pvfmkwupgtnan_mvml
9212 .{ .tag = @enumFromInt(2020), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9213 // __builtin_ve_vl_pvfmkwuple_mvl
9214 .{ .tag = @enumFromInt(2021), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9215 // __builtin_ve_vl_pvfmkwuple_mvml
9216 .{ .tag = @enumFromInt(2022), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9217 // __builtin_ve_vl_pvfmkwuplenan_mvl
9218 .{ .tag = @enumFromInt(2023), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9219 // __builtin_ve_vl_pvfmkwuplenan_mvml
9220 .{ .tag = @enumFromInt(2024), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9221 // __builtin_ve_vl_pvfmkwuplt_mvl
9222 .{ .tag = @enumFromInt(2025), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9223 // __builtin_ve_vl_pvfmkwuplt_mvml
9224 .{ .tag = @enumFromInt(2026), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9225 // __builtin_ve_vl_pvfmkwupltnan_mvl
9226 .{ .tag = @enumFromInt(2027), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9227 // __builtin_ve_vl_pvfmkwupltnan_mvml
9228 .{ .tag = @enumFromInt(2028), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9229 // __builtin_ve_vl_pvfmkwupnan_mvl
9230 .{ .tag = @enumFromInt(2029), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9231 // __builtin_ve_vl_pvfmkwupnan_mvml
9232 .{ .tag = @enumFromInt(2030), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9233 // __builtin_ve_vl_pvfmkwupne_mvl
9234 .{ .tag = @enumFromInt(2031), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9235 // __builtin_ve_vl_pvfmkwupne_mvml
9236 .{ .tag = @enumFromInt(2032), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9237 // __builtin_ve_vl_pvfmkwupnenan_mvl
9238 .{ .tag = @enumFromInt(2033), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9239 // __builtin_ve_vl_pvfmkwupnenan_mvml
9240 .{ .tag = @enumFromInt(2034), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9241 // __builtin_ve_vl_pvfmkwupnum_mvl
9242 .{ .tag = @enumFromInt(2035), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9243 // __builtin_ve_vl_pvfmkwupnum_mvml
9244 .{ .tag = @enumFromInt(2036), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9245 // __builtin_ve_vl_pvfmsb_vsvvMvl
9246 .{ .tag = @enumFromInt(2037), .properties = .{ .param_str = "V256dLUiV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9247 // __builtin_ve_vl_pvfmsb_vsvvl
9248 .{ .tag = @enumFromInt(2038), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9249 // __builtin_ve_vl_pvfmsb_vsvvvl
9250 .{ .tag = @enumFromInt(2039), .properties = .{ .param_str = "V256dLUiV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9251 // __builtin_ve_vl_pvfmsb_vvsvMvl
9252 .{ .tag = @enumFromInt(2040), .properties = .{ .param_str = "V256dV256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9253 // __builtin_ve_vl_pvfmsb_vvsvl
9254 .{ .tag = @enumFromInt(2041), .properties = .{ .param_str = "V256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9255 // __builtin_ve_vl_pvfmsb_vvsvvl
9256 .{ .tag = @enumFromInt(2042), .properties = .{ .param_str = "V256dV256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9257 // __builtin_ve_vl_pvfmsb_vvvvMvl
9258 .{ .tag = @enumFromInt(2043), .properties = .{ .param_str = "V256dV256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9259 // __builtin_ve_vl_pvfmsb_vvvvl
9260 .{ .tag = @enumFromInt(2044), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9261 // __builtin_ve_vl_pvfmsb_vvvvvl
9262 .{ .tag = @enumFromInt(2045), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9263 // __builtin_ve_vl_pvfmul_vsvMvl
9264 .{ .tag = @enumFromInt(2046), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9265 // __builtin_ve_vl_pvfmul_vsvl
9266 .{ .tag = @enumFromInt(2047), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9267 // __builtin_ve_vl_pvfmul_vsvvl
9268 .{ .tag = @enumFromInt(2048), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9269 // __builtin_ve_vl_pvfmul_vvvMvl
9270 .{ .tag = @enumFromInt(2049), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9271 // __builtin_ve_vl_pvfmul_vvvl
9272 .{ .tag = @enumFromInt(2050), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9273 // __builtin_ve_vl_pvfmul_vvvvl
9274 .{ .tag = @enumFromInt(2051), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9275 // __builtin_ve_vl_pvfnmad_vsvvMvl
9276 .{ .tag = @enumFromInt(2052), .properties = .{ .param_str = "V256dLUiV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9277 // __builtin_ve_vl_pvfnmad_vsvvl
9278 .{ .tag = @enumFromInt(2053), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9279 // __builtin_ve_vl_pvfnmad_vsvvvl
9280 .{ .tag = @enumFromInt(2054), .properties = .{ .param_str = "V256dLUiV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9281 // __builtin_ve_vl_pvfnmad_vvsvMvl
9282 .{ .tag = @enumFromInt(2055), .properties = .{ .param_str = "V256dV256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9283 // __builtin_ve_vl_pvfnmad_vvsvl
9284 .{ .tag = @enumFromInt(2056), .properties = .{ .param_str = "V256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9285 // __builtin_ve_vl_pvfnmad_vvsvvl
9286 .{ .tag = @enumFromInt(2057), .properties = .{ .param_str = "V256dV256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9287 // __builtin_ve_vl_pvfnmad_vvvvMvl
9288 .{ .tag = @enumFromInt(2058), .properties = .{ .param_str = "V256dV256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9289 // __builtin_ve_vl_pvfnmad_vvvvl
9290 .{ .tag = @enumFromInt(2059), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9291 // __builtin_ve_vl_pvfnmad_vvvvvl
9292 .{ .tag = @enumFromInt(2060), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9293 // __builtin_ve_vl_pvfnmsb_vsvvMvl
9294 .{ .tag = @enumFromInt(2061), .properties = .{ .param_str = "V256dLUiV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9295 // __builtin_ve_vl_pvfnmsb_vsvvl
9296 .{ .tag = @enumFromInt(2062), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9297 // __builtin_ve_vl_pvfnmsb_vsvvvl
9298 .{ .tag = @enumFromInt(2063), .properties = .{ .param_str = "V256dLUiV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9299 // __builtin_ve_vl_pvfnmsb_vvsvMvl
9300 .{ .tag = @enumFromInt(2064), .properties = .{ .param_str = "V256dV256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9301 // __builtin_ve_vl_pvfnmsb_vvsvl
9302 .{ .tag = @enumFromInt(2065), .properties = .{ .param_str = "V256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9303 // __builtin_ve_vl_pvfnmsb_vvsvvl
9304 .{ .tag = @enumFromInt(2066), .properties = .{ .param_str = "V256dV256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9305 // __builtin_ve_vl_pvfnmsb_vvvvMvl
9306 .{ .tag = @enumFromInt(2067), .properties = .{ .param_str = "V256dV256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9307 // __builtin_ve_vl_pvfnmsb_vvvvl
9308 .{ .tag = @enumFromInt(2068), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9309 // __builtin_ve_vl_pvfnmsb_vvvvvl
9310 .{ .tag = @enumFromInt(2069), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9311 // __builtin_ve_vl_pvfsub_vsvMvl
9312 .{ .tag = @enumFromInt(2070), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9313 // __builtin_ve_vl_pvfsub_vsvl
9314 .{ .tag = @enumFromInt(2071), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9315 // __builtin_ve_vl_pvfsub_vsvvl
9316 .{ .tag = @enumFromInt(2072), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9317 // __builtin_ve_vl_pvfsub_vvvMvl
9318 .{ .tag = @enumFromInt(2073), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9319 // __builtin_ve_vl_pvfsub_vvvl
9320 .{ .tag = @enumFromInt(2074), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9321 // __builtin_ve_vl_pvfsub_vvvvl
9322 .{ .tag = @enumFromInt(2075), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9323 // __builtin_ve_vl_pvldz_vvMvl
9324 .{ .tag = @enumFromInt(2076), .properties = .{ .param_str = "V256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9325 // __builtin_ve_vl_pvldz_vvl
9326 .{ .tag = @enumFromInt(2077), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9327 // __builtin_ve_vl_pvldz_vvvl
9328 .{ .tag = @enumFromInt(2078), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9329 // __builtin_ve_vl_pvldzlo_vvl
9330 .{ .tag = @enumFromInt(2079), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9331 // __builtin_ve_vl_pvldzlo_vvmvl
9332 .{ .tag = @enumFromInt(2080), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9333 // __builtin_ve_vl_pvldzlo_vvvl
9334 .{ .tag = @enumFromInt(2081), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9335 // __builtin_ve_vl_pvldzup_vvl
9336 .{ .tag = @enumFromInt(2082), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9337 // __builtin_ve_vl_pvldzup_vvmvl
9338 .{ .tag = @enumFromInt(2083), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9339 // __builtin_ve_vl_pvldzup_vvvl
9340 .{ .tag = @enumFromInt(2084), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9341 // __builtin_ve_vl_pvmaxs_vsvMvl
9342 .{ .tag = @enumFromInt(2085), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9343 // __builtin_ve_vl_pvmaxs_vsvl
9344 .{ .tag = @enumFromInt(2086), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9345 // __builtin_ve_vl_pvmaxs_vsvvl
9346 .{ .tag = @enumFromInt(2087), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9347 // __builtin_ve_vl_pvmaxs_vvvMvl
9348 .{ .tag = @enumFromInt(2088), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9349 // __builtin_ve_vl_pvmaxs_vvvl
9350 .{ .tag = @enumFromInt(2089), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9351 // __builtin_ve_vl_pvmaxs_vvvvl
9352 .{ .tag = @enumFromInt(2090), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9353 // __builtin_ve_vl_pvmins_vsvMvl
9354 .{ .tag = @enumFromInt(2091), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9355 // __builtin_ve_vl_pvmins_vsvl
9356 .{ .tag = @enumFromInt(2092), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9357 // __builtin_ve_vl_pvmins_vsvvl
9358 .{ .tag = @enumFromInt(2093), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9359 // __builtin_ve_vl_pvmins_vvvMvl
9360 .{ .tag = @enumFromInt(2094), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9361 // __builtin_ve_vl_pvmins_vvvl
9362 .{ .tag = @enumFromInt(2095), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9363 // __builtin_ve_vl_pvmins_vvvvl
9364 .{ .tag = @enumFromInt(2096), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9365 // __builtin_ve_vl_pvor_vsvMvl
9366 .{ .tag = @enumFromInt(2097), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9367 // __builtin_ve_vl_pvor_vsvl
9368 .{ .tag = @enumFromInt(2098), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9369 // __builtin_ve_vl_pvor_vsvvl
9370 .{ .tag = @enumFromInt(2099), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9371 // __builtin_ve_vl_pvor_vvvMvl
9372 .{ .tag = @enumFromInt(2100), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9373 // __builtin_ve_vl_pvor_vvvl
9374 .{ .tag = @enumFromInt(2101), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9375 // __builtin_ve_vl_pvor_vvvvl
9376 .{ .tag = @enumFromInt(2102), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9377 // __builtin_ve_vl_pvpcnt_vvMvl
9378 .{ .tag = @enumFromInt(2103), .properties = .{ .param_str = "V256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9379 // __builtin_ve_vl_pvpcnt_vvl
9380 .{ .tag = @enumFromInt(2104), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9381 // __builtin_ve_vl_pvpcnt_vvvl
9382 .{ .tag = @enumFromInt(2105), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9383 // __builtin_ve_vl_pvpcntlo_vvl
9384 .{ .tag = @enumFromInt(2106), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9385 // __builtin_ve_vl_pvpcntlo_vvmvl
9386 .{ .tag = @enumFromInt(2107), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9387 // __builtin_ve_vl_pvpcntlo_vvvl
9388 .{ .tag = @enumFromInt(2108), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9389 // __builtin_ve_vl_pvpcntup_vvl
9390 .{ .tag = @enumFromInt(2109), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9391 // __builtin_ve_vl_pvpcntup_vvmvl
9392 .{ .tag = @enumFromInt(2110), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9393 // __builtin_ve_vl_pvpcntup_vvvl
9394 .{ .tag = @enumFromInt(2111), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9395 // __builtin_ve_vl_pvrcp_vvl
9396 .{ .tag = @enumFromInt(2112), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9397 // __builtin_ve_vl_pvrcp_vvvl
9398 .{ .tag = @enumFromInt(2113), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9399 // __builtin_ve_vl_pvrsqrt_vvl
9400 .{ .tag = @enumFromInt(2114), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9401 // __builtin_ve_vl_pvrsqrt_vvvl
9402 .{ .tag = @enumFromInt(2115), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9403 // __builtin_ve_vl_pvrsqrtnex_vvl
9404 .{ .tag = @enumFromInt(2116), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9405 // __builtin_ve_vl_pvrsqrtnex_vvvl
9406 .{ .tag = @enumFromInt(2117), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9407 // __builtin_ve_vl_pvseq_vl
9408 .{ .tag = @enumFromInt(2118), .properties = .{ .param_str = "V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9409 // __builtin_ve_vl_pvseq_vvl
9410 .{ .tag = @enumFromInt(2119), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9411 // __builtin_ve_vl_pvseqlo_vl
9412 .{ .tag = @enumFromInt(2120), .properties = .{ .param_str = "V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9413 // __builtin_ve_vl_pvseqlo_vvl
9414 .{ .tag = @enumFromInt(2121), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9415 // __builtin_ve_vl_pvsequp_vl
9416 .{ .tag = @enumFromInt(2122), .properties = .{ .param_str = "V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9417 // __builtin_ve_vl_pvsequp_vvl
9418 .{ .tag = @enumFromInt(2123), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9419 // __builtin_ve_vl_pvsla_vvsMvl
9420 .{ .tag = @enumFromInt(2124), .properties = .{ .param_str = "V256dV256dLUiV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9421 // __builtin_ve_vl_pvsla_vvsl
9422 .{ .tag = @enumFromInt(2125), .properties = .{ .param_str = "V256dV256dLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9423 // __builtin_ve_vl_pvsla_vvsvl
9424 .{ .tag = @enumFromInt(2126), .properties = .{ .param_str = "V256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9425 // __builtin_ve_vl_pvsla_vvvMvl
9426 .{ .tag = @enumFromInt(2127), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9427 // __builtin_ve_vl_pvsla_vvvl
9428 .{ .tag = @enumFromInt(2128), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9429 // __builtin_ve_vl_pvsla_vvvvl
9430 .{ .tag = @enumFromInt(2129), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9431 // __builtin_ve_vl_pvsll_vvsMvl
9432 .{ .tag = @enumFromInt(2130), .properties = .{ .param_str = "V256dV256dLUiV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9433 // __builtin_ve_vl_pvsll_vvsl
9434 .{ .tag = @enumFromInt(2131), .properties = .{ .param_str = "V256dV256dLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9435 // __builtin_ve_vl_pvsll_vvsvl
9436 .{ .tag = @enumFromInt(2132), .properties = .{ .param_str = "V256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9437 // __builtin_ve_vl_pvsll_vvvMvl
9438 .{ .tag = @enumFromInt(2133), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9439 // __builtin_ve_vl_pvsll_vvvl
9440 .{ .tag = @enumFromInt(2134), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9441 // __builtin_ve_vl_pvsll_vvvvl
9442 .{ .tag = @enumFromInt(2135), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9443 // __builtin_ve_vl_pvsra_vvsMvl
9444 .{ .tag = @enumFromInt(2136), .properties = .{ .param_str = "V256dV256dLUiV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9445 // __builtin_ve_vl_pvsra_vvsl
9446 .{ .tag = @enumFromInt(2137), .properties = .{ .param_str = "V256dV256dLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9447 // __builtin_ve_vl_pvsra_vvsvl
9448 .{ .tag = @enumFromInt(2138), .properties = .{ .param_str = "V256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9449 // __builtin_ve_vl_pvsra_vvvMvl
9450 .{ .tag = @enumFromInt(2139), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9451 // __builtin_ve_vl_pvsra_vvvl
9452 .{ .tag = @enumFromInt(2140), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9453 // __builtin_ve_vl_pvsra_vvvvl
9454 .{ .tag = @enumFromInt(2141), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9455 // __builtin_ve_vl_pvsrl_vvsMvl
9456 .{ .tag = @enumFromInt(2142), .properties = .{ .param_str = "V256dV256dLUiV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9457 // __builtin_ve_vl_pvsrl_vvsl
9458 .{ .tag = @enumFromInt(2143), .properties = .{ .param_str = "V256dV256dLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9459 // __builtin_ve_vl_pvsrl_vvsvl
9460 .{ .tag = @enumFromInt(2144), .properties = .{ .param_str = "V256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9461 // __builtin_ve_vl_pvsrl_vvvMvl
9462 .{ .tag = @enumFromInt(2145), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9463 // __builtin_ve_vl_pvsrl_vvvl
9464 .{ .tag = @enumFromInt(2146), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9465 // __builtin_ve_vl_pvsrl_vvvvl
9466 .{ .tag = @enumFromInt(2147), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9467 // __builtin_ve_vl_pvsubs_vsvMvl
9468 .{ .tag = @enumFromInt(2148), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9469 // __builtin_ve_vl_pvsubs_vsvl
9470 .{ .tag = @enumFromInt(2149), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9471 // __builtin_ve_vl_pvsubs_vsvvl
9472 .{ .tag = @enumFromInt(2150), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9473 // __builtin_ve_vl_pvsubs_vvvMvl
9474 .{ .tag = @enumFromInt(2151), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9475 // __builtin_ve_vl_pvsubs_vvvl
9476 .{ .tag = @enumFromInt(2152), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9477 // __builtin_ve_vl_pvsubs_vvvvl
9478 .{ .tag = @enumFromInt(2153), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9479 // __builtin_ve_vl_pvsubu_vsvMvl
9480 .{ .tag = @enumFromInt(2154), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9481 // __builtin_ve_vl_pvsubu_vsvl
9482 .{ .tag = @enumFromInt(2155), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9483 // __builtin_ve_vl_pvsubu_vsvvl
9484 .{ .tag = @enumFromInt(2156), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9485 // __builtin_ve_vl_pvsubu_vvvMvl
9486 .{ .tag = @enumFromInt(2157), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9487 // __builtin_ve_vl_pvsubu_vvvl
9488 .{ .tag = @enumFromInt(2158), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9489 // __builtin_ve_vl_pvsubu_vvvvl
9490 .{ .tag = @enumFromInt(2159), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9491 // __builtin_ve_vl_pvxor_vsvMvl
9492 .{ .tag = @enumFromInt(2160), .properties = .{ .param_str = "V256dLUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9493 // __builtin_ve_vl_pvxor_vsvl
9494 .{ .tag = @enumFromInt(2161), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9495 // __builtin_ve_vl_pvxor_vsvvl
9496 .{ .tag = @enumFromInt(2162), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9497 // __builtin_ve_vl_pvxor_vvvMvl
9498 .{ .tag = @enumFromInt(2163), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9499 // __builtin_ve_vl_pvxor_vvvl
9500 .{ .tag = @enumFromInt(2164), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9501 // __builtin_ve_vl_pvxor_vvvvl
9502 .{ .tag = @enumFromInt(2165), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9503 // __builtin_ve_vl_scr_sss
9504 .{ .tag = @enumFromInt(2166), .properties = .{ .param_str = "vLUiLUiLUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9505 // __builtin_ve_vl_svm_sMs
9506 .{ .tag = @enumFromInt(2167), .properties = .{ .param_str = "LUiV512bLUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9507 // __builtin_ve_vl_svm_sms
9508 .{ .tag = @enumFromInt(2168), .properties = .{ .param_str = "LUiV256bLUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9509 // __builtin_ve_vl_svob
9510 .{ .tag = @enumFromInt(2169), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.vevl_gen) } },
9511 // __builtin_ve_vl_tovm_sml
9512 .{ .tag = @enumFromInt(2170), .properties = .{ .param_str = "LUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9513 // __builtin_ve_vl_tscr_ssss
9514 .{ .tag = @enumFromInt(2171), .properties = .{ .param_str = "LUiLUiLUiLUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9515 // __builtin_ve_vl_vaddsl_vsvl
9516 .{ .tag = @enumFromInt(2172), .properties = .{ .param_str = "V256dLiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9517 // __builtin_ve_vl_vaddsl_vsvmvl
9518 .{ .tag = @enumFromInt(2173), .properties = .{ .param_str = "V256dLiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9519 // __builtin_ve_vl_vaddsl_vsvvl
9520 .{ .tag = @enumFromInt(2174), .properties = .{ .param_str = "V256dLiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9521 // __builtin_ve_vl_vaddsl_vvvl
9522 .{ .tag = @enumFromInt(2175), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9523 // __builtin_ve_vl_vaddsl_vvvmvl
9524 .{ .tag = @enumFromInt(2176), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9525 // __builtin_ve_vl_vaddsl_vvvvl
9526 .{ .tag = @enumFromInt(2177), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9527 // __builtin_ve_vl_vaddswsx_vsvl
9528 .{ .tag = @enumFromInt(2178), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9529 // __builtin_ve_vl_vaddswsx_vsvmvl
9530 .{ .tag = @enumFromInt(2179), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9531 // __builtin_ve_vl_vaddswsx_vsvvl
9532 .{ .tag = @enumFromInt(2180), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9533 // __builtin_ve_vl_vaddswsx_vvvl
9534 .{ .tag = @enumFromInt(2181), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9535 // __builtin_ve_vl_vaddswsx_vvvmvl
9536 .{ .tag = @enumFromInt(2182), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9537 // __builtin_ve_vl_vaddswsx_vvvvl
9538 .{ .tag = @enumFromInt(2183), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9539 // __builtin_ve_vl_vaddswzx_vsvl
9540 .{ .tag = @enumFromInt(2184), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9541 // __builtin_ve_vl_vaddswzx_vsvmvl
9542 .{ .tag = @enumFromInt(2185), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9543 // __builtin_ve_vl_vaddswzx_vsvvl
9544 .{ .tag = @enumFromInt(2186), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9545 // __builtin_ve_vl_vaddswzx_vvvl
9546 .{ .tag = @enumFromInt(2187), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9547 // __builtin_ve_vl_vaddswzx_vvvmvl
9548 .{ .tag = @enumFromInt(2188), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9549 // __builtin_ve_vl_vaddswzx_vvvvl
9550 .{ .tag = @enumFromInt(2189), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9551 // __builtin_ve_vl_vaddul_vsvl
9552 .{ .tag = @enumFromInt(2190), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9553 // __builtin_ve_vl_vaddul_vsvmvl
9554 .{ .tag = @enumFromInt(2191), .properties = .{ .param_str = "V256dLUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9555 // __builtin_ve_vl_vaddul_vsvvl
9556 .{ .tag = @enumFromInt(2192), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9557 // __builtin_ve_vl_vaddul_vvvl
9558 .{ .tag = @enumFromInt(2193), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9559 // __builtin_ve_vl_vaddul_vvvmvl
9560 .{ .tag = @enumFromInt(2194), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9561 // __builtin_ve_vl_vaddul_vvvvl
9562 .{ .tag = @enumFromInt(2195), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9563 // __builtin_ve_vl_vadduw_vsvl
9564 .{ .tag = @enumFromInt(2196), .properties = .{ .param_str = "V256dUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9565 // __builtin_ve_vl_vadduw_vsvmvl
9566 .{ .tag = @enumFromInt(2197), .properties = .{ .param_str = "V256dUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9567 // __builtin_ve_vl_vadduw_vsvvl
9568 .{ .tag = @enumFromInt(2198), .properties = .{ .param_str = "V256dUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9569 // __builtin_ve_vl_vadduw_vvvl
9570 .{ .tag = @enumFromInt(2199), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9571 // __builtin_ve_vl_vadduw_vvvmvl
9572 .{ .tag = @enumFromInt(2200), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9573 // __builtin_ve_vl_vadduw_vvvvl
9574 .{ .tag = @enumFromInt(2201), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9575 // __builtin_ve_vl_vand_vsvl
9576 .{ .tag = @enumFromInt(2202), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9577 // __builtin_ve_vl_vand_vsvmvl
9578 .{ .tag = @enumFromInt(2203), .properties = .{ .param_str = "V256dLUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9579 // __builtin_ve_vl_vand_vsvvl
9580 .{ .tag = @enumFromInt(2204), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9581 // __builtin_ve_vl_vand_vvvl
9582 .{ .tag = @enumFromInt(2205), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9583 // __builtin_ve_vl_vand_vvvmvl
9584 .{ .tag = @enumFromInt(2206), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9585 // __builtin_ve_vl_vand_vvvvl
9586 .{ .tag = @enumFromInt(2207), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9587 // __builtin_ve_vl_vbrdd_vsl
9588 .{ .tag = @enumFromInt(2208), .properties = .{ .param_str = "V256ddUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9589 // __builtin_ve_vl_vbrdd_vsmvl
9590 .{ .tag = @enumFromInt(2209), .properties = .{ .param_str = "V256ddV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9591 // __builtin_ve_vl_vbrdd_vsvl
9592 .{ .tag = @enumFromInt(2210), .properties = .{ .param_str = "V256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9593 // __builtin_ve_vl_vbrdl_vsl
9594 .{ .tag = @enumFromInt(2211), .properties = .{ .param_str = "V256dLiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9595 // __builtin_ve_vl_vbrdl_vsmvl
9596 .{ .tag = @enumFromInt(2212), .properties = .{ .param_str = "V256dLiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9597 // __builtin_ve_vl_vbrdl_vsvl
9598 .{ .tag = @enumFromInt(2213), .properties = .{ .param_str = "V256dLiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9599 // __builtin_ve_vl_vbrds_vsl
9600 .{ .tag = @enumFromInt(2214), .properties = .{ .param_str = "V256dfUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9601 // __builtin_ve_vl_vbrds_vsmvl
9602 .{ .tag = @enumFromInt(2215), .properties = .{ .param_str = "V256dfV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9603 // __builtin_ve_vl_vbrds_vsvl
9604 .{ .tag = @enumFromInt(2216), .properties = .{ .param_str = "V256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9605 // __builtin_ve_vl_vbrdw_vsl
9606 .{ .tag = @enumFromInt(2217), .properties = .{ .param_str = "V256diUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9607 // __builtin_ve_vl_vbrdw_vsmvl
9608 .{ .tag = @enumFromInt(2218), .properties = .{ .param_str = "V256diV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9609 // __builtin_ve_vl_vbrdw_vsvl
9610 .{ .tag = @enumFromInt(2219), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9611 // __builtin_ve_vl_vbrv_vvl
9612 .{ .tag = @enumFromInt(2220), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9613 // __builtin_ve_vl_vbrv_vvmvl
9614 .{ .tag = @enumFromInt(2221), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9615 // __builtin_ve_vl_vbrv_vvvl
9616 .{ .tag = @enumFromInt(2222), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9617 // __builtin_ve_vl_vcmpsl_vsvl
9618 .{ .tag = @enumFromInt(2223), .properties = .{ .param_str = "V256dLiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9619 // __builtin_ve_vl_vcmpsl_vsvmvl
9620 .{ .tag = @enumFromInt(2224), .properties = .{ .param_str = "V256dLiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9621 // __builtin_ve_vl_vcmpsl_vsvvl
9622 .{ .tag = @enumFromInt(2225), .properties = .{ .param_str = "V256dLiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9623 // __builtin_ve_vl_vcmpsl_vvvl
9624 .{ .tag = @enumFromInt(2226), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9625 // __builtin_ve_vl_vcmpsl_vvvmvl
9626 .{ .tag = @enumFromInt(2227), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9627 // __builtin_ve_vl_vcmpsl_vvvvl
9628 .{ .tag = @enumFromInt(2228), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9629 // __builtin_ve_vl_vcmpswsx_vsvl
9630 .{ .tag = @enumFromInt(2229), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9631 // __builtin_ve_vl_vcmpswsx_vsvmvl
9632 .{ .tag = @enumFromInt(2230), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9633 // __builtin_ve_vl_vcmpswsx_vsvvl
9634 .{ .tag = @enumFromInt(2231), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9635 // __builtin_ve_vl_vcmpswsx_vvvl
9636 .{ .tag = @enumFromInt(2232), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9637 // __builtin_ve_vl_vcmpswsx_vvvmvl
9638 .{ .tag = @enumFromInt(2233), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9639 // __builtin_ve_vl_vcmpswsx_vvvvl
9640 .{ .tag = @enumFromInt(2234), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9641 // __builtin_ve_vl_vcmpswzx_vsvl
9642 .{ .tag = @enumFromInt(2235), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9643 // __builtin_ve_vl_vcmpswzx_vsvmvl
9644 .{ .tag = @enumFromInt(2236), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9645 // __builtin_ve_vl_vcmpswzx_vsvvl
9646 .{ .tag = @enumFromInt(2237), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9647 // __builtin_ve_vl_vcmpswzx_vvvl
9648 .{ .tag = @enumFromInt(2238), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9649 // __builtin_ve_vl_vcmpswzx_vvvmvl
9650 .{ .tag = @enumFromInt(2239), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9651 // __builtin_ve_vl_vcmpswzx_vvvvl
9652 .{ .tag = @enumFromInt(2240), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9653 // __builtin_ve_vl_vcmpul_vsvl
9654 .{ .tag = @enumFromInt(2241), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9655 // __builtin_ve_vl_vcmpul_vsvmvl
9656 .{ .tag = @enumFromInt(2242), .properties = .{ .param_str = "V256dLUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9657 // __builtin_ve_vl_vcmpul_vsvvl
9658 .{ .tag = @enumFromInt(2243), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9659 // __builtin_ve_vl_vcmpul_vvvl
9660 .{ .tag = @enumFromInt(2244), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9661 // __builtin_ve_vl_vcmpul_vvvmvl
9662 .{ .tag = @enumFromInt(2245), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9663 // __builtin_ve_vl_vcmpul_vvvvl
9664 .{ .tag = @enumFromInt(2246), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9665 // __builtin_ve_vl_vcmpuw_vsvl
9666 .{ .tag = @enumFromInt(2247), .properties = .{ .param_str = "V256dUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9667 // __builtin_ve_vl_vcmpuw_vsvmvl
9668 .{ .tag = @enumFromInt(2248), .properties = .{ .param_str = "V256dUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9669 // __builtin_ve_vl_vcmpuw_vsvvl
9670 .{ .tag = @enumFromInt(2249), .properties = .{ .param_str = "V256dUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9671 // __builtin_ve_vl_vcmpuw_vvvl
9672 .{ .tag = @enumFromInt(2250), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9673 // __builtin_ve_vl_vcmpuw_vvvmvl
9674 .{ .tag = @enumFromInt(2251), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9675 // __builtin_ve_vl_vcmpuw_vvvvl
9676 .{ .tag = @enumFromInt(2252), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9677 // __builtin_ve_vl_vcp_vvmvl
9678 .{ .tag = @enumFromInt(2253), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9679 // __builtin_ve_vl_vcvtdl_vvl
9680 .{ .tag = @enumFromInt(2254), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9681 // __builtin_ve_vl_vcvtdl_vvvl
9682 .{ .tag = @enumFromInt(2255), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9683 // __builtin_ve_vl_vcvtds_vvl
9684 .{ .tag = @enumFromInt(2256), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9685 // __builtin_ve_vl_vcvtds_vvvl
9686 .{ .tag = @enumFromInt(2257), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9687 // __builtin_ve_vl_vcvtdw_vvl
9688 .{ .tag = @enumFromInt(2258), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9689 // __builtin_ve_vl_vcvtdw_vvvl
9690 .{ .tag = @enumFromInt(2259), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9691 // __builtin_ve_vl_vcvtld_vvl
9692 .{ .tag = @enumFromInt(2260), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9693 // __builtin_ve_vl_vcvtld_vvmvl
9694 .{ .tag = @enumFromInt(2261), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9695 // __builtin_ve_vl_vcvtld_vvvl
9696 .{ .tag = @enumFromInt(2262), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9697 // __builtin_ve_vl_vcvtldrz_vvl
9698 .{ .tag = @enumFromInt(2263), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9699 // __builtin_ve_vl_vcvtldrz_vvmvl
9700 .{ .tag = @enumFromInt(2264), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9701 // __builtin_ve_vl_vcvtldrz_vvvl
9702 .{ .tag = @enumFromInt(2265), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9703 // __builtin_ve_vl_vcvtsd_vvl
9704 .{ .tag = @enumFromInt(2266), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9705 // __builtin_ve_vl_vcvtsd_vvvl
9706 .{ .tag = @enumFromInt(2267), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9707 // __builtin_ve_vl_vcvtsw_vvl
9708 .{ .tag = @enumFromInt(2268), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9709 // __builtin_ve_vl_vcvtsw_vvvl
9710 .{ .tag = @enumFromInt(2269), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9711 // __builtin_ve_vl_vcvtwdsx_vvl
9712 .{ .tag = @enumFromInt(2270), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9713 // __builtin_ve_vl_vcvtwdsx_vvmvl
9714 .{ .tag = @enumFromInt(2271), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9715 // __builtin_ve_vl_vcvtwdsx_vvvl
9716 .{ .tag = @enumFromInt(2272), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9717 // __builtin_ve_vl_vcvtwdsxrz_vvl
9718 .{ .tag = @enumFromInt(2273), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9719 // __builtin_ve_vl_vcvtwdsxrz_vvmvl
9720 .{ .tag = @enumFromInt(2274), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9721 // __builtin_ve_vl_vcvtwdsxrz_vvvl
9722 .{ .tag = @enumFromInt(2275), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9723 // __builtin_ve_vl_vcvtwdzx_vvl
9724 .{ .tag = @enumFromInt(2276), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9725 // __builtin_ve_vl_vcvtwdzx_vvmvl
9726 .{ .tag = @enumFromInt(2277), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9727 // __builtin_ve_vl_vcvtwdzx_vvvl
9728 .{ .tag = @enumFromInt(2278), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9729 // __builtin_ve_vl_vcvtwdzxrz_vvl
9730 .{ .tag = @enumFromInt(2279), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9731 // __builtin_ve_vl_vcvtwdzxrz_vvmvl
9732 .{ .tag = @enumFromInt(2280), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9733 // __builtin_ve_vl_vcvtwdzxrz_vvvl
9734 .{ .tag = @enumFromInt(2281), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9735 // __builtin_ve_vl_vcvtwssx_vvl
9736 .{ .tag = @enumFromInt(2282), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9737 // __builtin_ve_vl_vcvtwssx_vvmvl
9738 .{ .tag = @enumFromInt(2283), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9739 // __builtin_ve_vl_vcvtwssx_vvvl
9740 .{ .tag = @enumFromInt(2284), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9741 // __builtin_ve_vl_vcvtwssxrz_vvl
9742 .{ .tag = @enumFromInt(2285), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9743 // __builtin_ve_vl_vcvtwssxrz_vvmvl
9744 .{ .tag = @enumFromInt(2286), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9745 // __builtin_ve_vl_vcvtwssxrz_vvvl
9746 .{ .tag = @enumFromInt(2287), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9747 // __builtin_ve_vl_vcvtwszx_vvl
9748 .{ .tag = @enumFromInt(2288), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9749 // __builtin_ve_vl_vcvtwszx_vvmvl
9750 .{ .tag = @enumFromInt(2289), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9751 // __builtin_ve_vl_vcvtwszx_vvvl
9752 .{ .tag = @enumFromInt(2290), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9753 // __builtin_ve_vl_vcvtwszxrz_vvl
9754 .{ .tag = @enumFromInt(2291), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9755 // __builtin_ve_vl_vcvtwszxrz_vvmvl
9756 .{ .tag = @enumFromInt(2292), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9757 // __builtin_ve_vl_vcvtwszxrz_vvvl
9758 .{ .tag = @enumFromInt(2293), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9759 // __builtin_ve_vl_vdivsl_vsvl
9760 .{ .tag = @enumFromInt(2294), .properties = .{ .param_str = "V256dLiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9761 // __builtin_ve_vl_vdivsl_vsvmvl
9762 .{ .tag = @enumFromInt(2295), .properties = .{ .param_str = "V256dLiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9763 // __builtin_ve_vl_vdivsl_vsvvl
9764 .{ .tag = @enumFromInt(2296), .properties = .{ .param_str = "V256dLiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9765 // __builtin_ve_vl_vdivsl_vvsl
9766 .{ .tag = @enumFromInt(2297), .properties = .{ .param_str = "V256dV256dLiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9767 // __builtin_ve_vl_vdivsl_vvsmvl
9768 .{ .tag = @enumFromInt(2298), .properties = .{ .param_str = "V256dV256dLiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9769 // __builtin_ve_vl_vdivsl_vvsvl
9770 .{ .tag = @enumFromInt(2299), .properties = .{ .param_str = "V256dV256dLiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9771 // __builtin_ve_vl_vdivsl_vvvl
9772 .{ .tag = @enumFromInt(2300), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9773 // __builtin_ve_vl_vdivsl_vvvmvl
9774 .{ .tag = @enumFromInt(2301), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9775 // __builtin_ve_vl_vdivsl_vvvvl
9776 .{ .tag = @enumFromInt(2302), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9777 // __builtin_ve_vl_vdivswsx_vsvl
9778 .{ .tag = @enumFromInt(2303), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9779 // __builtin_ve_vl_vdivswsx_vsvmvl
9780 .{ .tag = @enumFromInt(2304), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9781 // __builtin_ve_vl_vdivswsx_vsvvl
9782 .{ .tag = @enumFromInt(2305), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9783 // __builtin_ve_vl_vdivswsx_vvsl
9784 .{ .tag = @enumFromInt(2306), .properties = .{ .param_str = "V256dV256diUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9785 // __builtin_ve_vl_vdivswsx_vvsmvl
9786 .{ .tag = @enumFromInt(2307), .properties = .{ .param_str = "V256dV256diV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9787 // __builtin_ve_vl_vdivswsx_vvsvl
9788 .{ .tag = @enumFromInt(2308), .properties = .{ .param_str = "V256dV256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9789 // __builtin_ve_vl_vdivswsx_vvvl
9790 .{ .tag = @enumFromInt(2309), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9791 // __builtin_ve_vl_vdivswsx_vvvmvl
9792 .{ .tag = @enumFromInt(2310), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9793 // __builtin_ve_vl_vdivswsx_vvvvl
9794 .{ .tag = @enumFromInt(2311), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9795 // __builtin_ve_vl_vdivswzx_vsvl
9796 .{ .tag = @enumFromInt(2312), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9797 // __builtin_ve_vl_vdivswzx_vsvmvl
9798 .{ .tag = @enumFromInt(2313), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9799 // __builtin_ve_vl_vdivswzx_vsvvl
9800 .{ .tag = @enumFromInt(2314), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9801 // __builtin_ve_vl_vdivswzx_vvsl
9802 .{ .tag = @enumFromInt(2315), .properties = .{ .param_str = "V256dV256diUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9803 // __builtin_ve_vl_vdivswzx_vvsmvl
9804 .{ .tag = @enumFromInt(2316), .properties = .{ .param_str = "V256dV256diV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9805 // __builtin_ve_vl_vdivswzx_vvsvl
9806 .{ .tag = @enumFromInt(2317), .properties = .{ .param_str = "V256dV256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9807 // __builtin_ve_vl_vdivswzx_vvvl
9808 .{ .tag = @enumFromInt(2318), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9809 // __builtin_ve_vl_vdivswzx_vvvmvl
9810 .{ .tag = @enumFromInt(2319), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9811 // __builtin_ve_vl_vdivswzx_vvvvl
9812 .{ .tag = @enumFromInt(2320), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9813 // __builtin_ve_vl_vdivul_vsvl
9814 .{ .tag = @enumFromInt(2321), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9815 // __builtin_ve_vl_vdivul_vsvmvl
9816 .{ .tag = @enumFromInt(2322), .properties = .{ .param_str = "V256dLUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9817 // __builtin_ve_vl_vdivul_vsvvl
9818 .{ .tag = @enumFromInt(2323), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9819 // __builtin_ve_vl_vdivul_vvsl
9820 .{ .tag = @enumFromInt(2324), .properties = .{ .param_str = "V256dV256dLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9821 // __builtin_ve_vl_vdivul_vvsmvl
9822 .{ .tag = @enumFromInt(2325), .properties = .{ .param_str = "V256dV256dLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9823 // __builtin_ve_vl_vdivul_vvsvl
9824 .{ .tag = @enumFromInt(2326), .properties = .{ .param_str = "V256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9825 // __builtin_ve_vl_vdivul_vvvl
9826 .{ .tag = @enumFromInt(2327), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9827 // __builtin_ve_vl_vdivul_vvvmvl
9828 .{ .tag = @enumFromInt(2328), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9829 // __builtin_ve_vl_vdivul_vvvvl
9830 .{ .tag = @enumFromInt(2329), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9831 // __builtin_ve_vl_vdivuw_vsvl
9832 .{ .tag = @enumFromInt(2330), .properties = .{ .param_str = "V256dUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9833 // __builtin_ve_vl_vdivuw_vsvmvl
9834 .{ .tag = @enumFromInt(2331), .properties = .{ .param_str = "V256dUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9835 // __builtin_ve_vl_vdivuw_vsvvl
9836 .{ .tag = @enumFromInt(2332), .properties = .{ .param_str = "V256dUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9837 // __builtin_ve_vl_vdivuw_vvsl
9838 .{ .tag = @enumFromInt(2333), .properties = .{ .param_str = "V256dV256dUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9839 // __builtin_ve_vl_vdivuw_vvsmvl
9840 .{ .tag = @enumFromInt(2334), .properties = .{ .param_str = "V256dV256dUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9841 // __builtin_ve_vl_vdivuw_vvsvl
9842 .{ .tag = @enumFromInt(2335), .properties = .{ .param_str = "V256dV256dUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9843 // __builtin_ve_vl_vdivuw_vvvl
9844 .{ .tag = @enumFromInt(2336), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9845 // __builtin_ve_vl_vdivuw_vvvmvl
9846 .{ .tag = @enumFromInt(2337), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9847 // __builtin_ve_vl_vdivuw_vvvvl
9848 .{ .tag = @enumFromInt(2338), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9849 // __builtin_ve_vl_veqv_vsvl
9850 .{ .tag = @enumFromInt(2339), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9851 // __builtin_ve_vl_veqv_vsvmvl
9852 .{ .tag = @enumFromInt(2340), .properties = .{ .param_str = "V256dLUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9853 // __builtin_ve_vl_veqv_vsvvl
9854 .{ .tag = @enumFromInt(2341), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9855 // __builtin_ve_vl_veqv_vvvl
9856 .{ .tag = @enumFromInt(2342), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9857 // __builtin_ve_vl_veqv_vvvmvl
9858 .{ .tag = @enumFromInt(2343), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9859 // __builtin_ve_vl_veqv_vvvvl
9860 .{ .tag = @enumFromInt(2344), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9861 // __builtin_ve_vl_vex_vvmvl
9862 .{ .tag = @enumFromInt(2345), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9863 // __builtin_ve_vl_vfaddd_vsvl
9864 .{ .tag = @enumFromInt(2346), .properties = .{ .param_str = "V256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9865 // __builtin_ve_vl_vfaddd_vsvmvl
9866 .{ .tag = @enumFromInt(2347), .properties = .{ .param_str = "V256ddV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9867 // __builtin_ve_vl_vfaddd_vsvvl
9868 .{ .tag = @enumFromInt(2348), .properties = .{ .param_str = "V256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9869 // __builtin_ve_vl_vfaddd_vvvl
9870 .{ .tag = @enumFromInt(2349), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9871 // __builtin_ve_vl_vfaddd_vvvmvl
9872 .{ .tag = @enumFromInt(2350), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9873 // __builtin_ve_vl_vfaddd_vvvvl
9874 .{ .tag = @enumFromInt(2351), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9875 // __builtin_ve_vl_vfadds_vsvl
9876 .{ .tag = @enumFromInt(2352), .properties = .{ .param_str = "V256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9877 // __builtin_ve_vl_vfadds_vsvmvl
9878 .{ .tag = @enumFromInt(2353), .properties = .{ .param_str = "V256dfV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9879 // __builtin_ve_vl_vfadds_vsvvl
9880 .{ .tag = @enumFromInt(2354), .properties = .{ .param_str = "V256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9881 // __builtin_ve_vl_vfadds_vvvl
9882 .{ .tag = @enumFromInt(2355), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9883 // __builtin_ve_vl_vfadds_vvvmvl
9884 .{ .tag = @enumFromInt(2356), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9885 // __builtin_ve_vl_vfadds_vvvvl
9886 .{ .tag = @enumFromInt(2357), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9887 // __builtin_ve_vl_vfcmpd_vsvl
9888 .{ .tag = @enumFromInt(2358), .properties = .{ .param_str = "V256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9889 // __builtin_ve_vl_vfcmpd_vsvmvl
9890 .{ .tag = @enumFromInt(2359), .properties = .{ .param_str = "V256ddV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9891 // __builtin_ve_vl_vfcmpd_vsvvl
9892 .{ .tag = @enumFromInt(2360), .properties = .{ .param_str = "V256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9893 // __builtin_ve_vl_vfcmpd_vvvl
9894 .{ .tag = @enumFromInt(2361), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9895 // __builtin_ve_vl_vfcmpd_vvvmvl
9896 .{ .tag = @enumFromInt(2362), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9897 // __builtin_ve_vl_vfcmpd_vvvvl
9898 .{ .tag = @enumFromInt(2363), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9899 // __builtin_ve_vl_vfcmps_vsvl
9900 .{ .tag = @enumFromInt(2364), .properties = .{ .param_str = "V256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9901 // __builtin_ve_vl_vfcmps_vsvmvl
9902 .{ .tag = @enumFromInt(2365), .properties = .{ .param_str = "V256dfV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9903 // __builtin_ve_vl_vfcmps_vsvvl
9904 .{ .tag = @enumFromInt(2366), .properties = .{ .param_str = "V256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9905 // __builtin_ve_vl_vfcmps_vvvl
9906 .{ .tag = @enumFromInt(2367), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9907 // __builtin_ve_vl_vfcmps_vvvmvl
9908 .{ .tag = @enumFromInt(2368), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9909 // __builtin_ve_vl_vfcmps_vvvvl
9910 .{ .tag = @enumFromInt(2369), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9911 // __builtin_ve_vl_vfdivd_vsvl
9912 .{ .tag = @enumFromInt(2370), .properties = .{ .param_str = "V256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9913 // __builtin_ve_vl_vfdivd_vsvmvl
9914 .{ .tag = @enumFromInt(2371), .properties = .{ .param_str = "V256ddV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9915 // __builtin_ve_vl_vfdivd_vsvvl
9916 .{ .tag = @enumFromInt(2372), .properties = .{ .param_str = "V256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9917 // __builtin_ve_vl_vfdivd_vvvl
9918 .{ .tag = @enumFromInt(2373), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9919 // __builtin_ve_vl_vfdivd_vvvmvl
9920 .{ .tag = @enumFromInt(2374), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9921 // __builtin_ve_vl_vfdivd_vvvvl
9922 .{ .tag = @enumFromInt(2375), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9923 // __builtin_ve_vl_vfdivs_vsvl
9924 .{ .tag = @enumFromInt(2376), .properties = .{ .param_str = "V256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9925 // __builtin_ve_vl_vfdivs_vsvmvl
9926 .{ .tag = @enumFromInt(2377), .properties = .{ .param_str = "V256dfV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9927 // __builtin_ve_vl_vfdivs_vsvvl
9928 .{ .tag = @enumFromInt(2378), .properties = .{ .param_str = "V256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9929 // __builtin_ve_vl_vfdivs_vvvl
9930 .{ .tag = @enumFromInt(2379), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9931 // __builtin_ve_vl_vfdivs_vvvmvl
9932 .{ .tag = @enumFromInt(2380), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9933 // __builtin_ve_vl_vfdivs_vvvvl
9934 .{ .tag = @enumFromInt(2381), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9935 // __builtin_ve_vl_vfmadd_vsvvl
9936 .{ .tag = @enumFromInt(2382), .properties = .{ .param_str = "V256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9937 // __builtin_ve_vl_vfmadd_vsvvmvl
9938 .{ .tag = @enumFromInt(2383), .properties = .{ .param_str = "V256ddV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9939 // __builtin_ve_vl_vfmadd_vsvvvl
9940 .{ .tag = @enumFromInt(2384), .properties = .{ .param_str = "V256ddV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9941 // __builtin_ve_vl_vfmadd_vvsvl
9942 .{ .tag = @enumFromInt(2385), .properties = .{ .param_str = "V256dV256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9943 // __builtin_ve_vl_vfmadd_vvsvmvl
9944 .{ .tag = @enumFromInt(2386), .properties = .{ .param_str = "V256dV256ddV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9945 // __builtin_ve_vl_vfmadd_vvsvvl
9946 .{ .tag = @enumFromInt(2387), .properties = .{ .param_str = "V256dV256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9947 // __builtin_ve_vl_vfmadd_vvvvl
9948 .{ .tag = @enumFromInt(2388), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9949 // __builtin_ve_vl_vfmadd_vvvvmvl
9950 .{ .tag = @enumFromInt(2389), .properties = .{ .param_str = "V256dV256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9951 // __builtin_ve_vl_vfmadd_vvvvvl
9952 .{ .tag = @enumFromInt(2390), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9953 // __builtin_ve_vl_vfmads_vsvvl
9954 .{ .tag = @enumFromInt(2391), .properties = .{ .param_str = "V256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9955 // __builtin_ve_vl_vfmads_vsvvmvl
9956 .{ .tag = @enumFromInt(2392), .properties = .{ .param_str = "V256dfV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9957 // __builtin_ve_vl_vfmads_vsvvvl
9958 .{ .tag = @enumFromInt(2393), .properties = .{ .param_str = "V256dfV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9959 // __builtin_ve_vl_vfmads_vvsvl
9960 .{ .tag = @enumFromInt(2394), .properties = .{ .param_str = "V256dV256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9961 // __builtin_ve_vl_vfmads_vvsvmvl
9962 .{ .tag = @enumFromInt(2395), .properties = .{ .param_str = "V256dV256dfV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9963 // __builtin_ve_vl_vfmads_vvsvvl
9964 .{ .tag = @enumFromInt(2396), .properties = .{ .param_str = "V256dV256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9965 // __builtin_ve_vl_vfmads_vvvvl
9966 .{ .tag = @enumFromInt(2397), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9967 // __builtin_ve_vl_vfmads_vvvvmvl
9968 .{ .tag = @enumFromInt(2398), .properties = .{ .param_str = "V256dV256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9969 // __builtin_ve_vl_vfmads_vvvvvl
9970 .{ .tag = @enumFromInt(2399), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9971 // __builtin_ve_vl_vfmaxd_vsvl
9972 .{ .tag = @enumFromInt(2400), .properties = .{ .param_str = "V256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9973 // __builtin_ve_vl_vfmaxd_vsvmvl
9974 .{ .tag = @enumFromInt(2401), .properties = .{ .param_str = "V256ddV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9975 // __builtin_ve_vl_vfmaxd_vsvvl
9976 .{ .tag = @enumFromInt(2402), .properties = .{ .param_str = "V256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9977 // __builtin_ve_vl_vfmaxd_vvvl
9978 .{ .tag = @enumFromInt(2403), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9979 // __builtin_ve_vl_vfmaxd_vvvmvl
9980 .{ .tag = @enumFromInt(2404), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9981 // __builtin_ve_vl_vfmaxd_vvvvl
9982 .{ .tag = @enumFromInt(2405), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9983 // __builtin_ve_vl_vfmaxs_vsvl
9984 .{ .tag = @enumFromInt(2406), .properties = .{ .param_str = "V256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9985 // __builtin_ve_vl_vfmaxs_vsvmvl
9986 .{ .tag = @enumFromInt(2407), .properties = .{ .param_str = "V256dfV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9987 // __builtin_ve_vl_vfmaxs_vsvvl
9988 .{ .tag = @enumFromInt(2408), .properties = .{ .param_str = "V256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9989 // __builtin_ve_vl_vfmaxs_vvvl
9990 .{ .tag = @enumFromInt(2409), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9991 // __builtin_ve_vl_vfmaxs_vvvmvl
9992 .{ .tag = @enumFromInt(2410), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9993 // __builtin_ve_vl_vfmaxs_vvvvl
9994 .{ .tag = @enumFromInt(2411), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9995 // __builtin_ve_vl_vfmind_vsvl
9996 .{ .tag = @enumFromInt(2412), .properties = .{ .param_str = "V256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9997 // __builtin_ve_vl_vfmind_vsvmvl
9998 .{ .tag = @enumFromInt(2413), .properties = .{ .param_str = "V256ddV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
9999 // __builtin_ve_vl_vfmind_vsvvl
10000 .{ .tag = @enumFromInt(2414), .properties = .{ .param_str = "V256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10001 // __builtin_ve_vl_vfmind_vvvl
10002 .{ .tag = @enumFromInt(2415), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10003 // __builtin_ve_vl_vfmind_vvvmvl
10004 .{ .tag = @enumFromInt(2416), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10005 // __builtin_ve_vl_vfmind_vvvvl
10006 .{ .tag = @enumFromInt(2417), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10007 // __builtin_ve_vl_vfmins_vsvl
10008 .{ .tag = @enumFromInt(2418), .properties = .{ .param_str = "V256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10009 // __builtin_ve_vl_vfmins_vsvmvl
10010 .{ .tag = @enumFromInt(2419), .properties = .{ .param_str = "V256dfV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10011 // __builtin_ve_vl_vfmins_vsvvl
10012 .{ .tag = @enumFromInt(2420), .properties = .{ .param_str = "V256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10013 // __builtin_ve_vl_vfmins_vvvl
10014 .{ .tag = @enumFromInt(2421), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10015 // __builtin_ve_vl_vfmins_vvvmvl
10016 .{ .tag = @enumFromInt(2422), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10017 // __builtin_ve_vl_vfmins_vvvvl
10018 .{ .tag = @enumFromInt(2423), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10019 // __builtin_ve_vl_vfmkdeq_mvl
10020 .{ .tag = @enumFromInt(2424), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10021 // __builtin_ve_vl_vfmkdeq_mvml
10022 .{ .tag = @enumFromInt(2425), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10023 // __builtin_ve_vl_vfmkdeqnan_mvl
10024 .{ .tag = @enumFromInt(2426), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10025 // __builtin_ve_vl_vfmkdeqnan_mvml
10026 .{ .tag = @enumFromInt(2427), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10027 // __builtin_ve_vl_vfmkdge_mvl
10028 .{ .tag = @enumFromInt(2428), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10029 // __builtin_ve_vl_vfmkdge_mvml
10030 .{ .tag = @enumFromInt(2429), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10031 // __builtin_ve_vl_vfmkdgenan_mvl
10032 .{ .tag = @enumFromInt(2430), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10033 // __builtin_ve_vl_vfmkdgenan_mvml
10034 .{ .tag = @enumFromInt(2431), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10035 // __builtin_ve_vl_vfmkdgt_mvl
10036 .{ .tag = @enumFromInt(2432), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10037 // __builtin_ve_vl_vfmkdgt_mvml
10038 .{ .tag = @enumFromInt(2433), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10039 // __builtin_ve_vl_vfmkdgtnan_mvl
10040 .{ .tag = @enumFromInt(2434), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10041 // __builtin_ve_vl_vfmkdgtnan_mvml
10042 .{ .tag = @enumFromInt(2435), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10043 // __builtin_ve_vl_vfmkdle_mvl
10044 .{ .tag = @enumFromInt(2436), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10045 // __builtin_ve_vl_vfmkdle_mvml
10046 .{ .tag = @enumFromInt(2437), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10047 // __builtin_ve_vl_vfmkdlenan_mvl
10048 .{ .tag = @enumFromInt(2438), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10049 // __builtin_ve_vl_vfmkdlenan_mvml
10050 .{ .tag = @enumFromInt(2439), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10051 // __builtin_ve_vl_vfmkdlt_mvl
10052 .{ .tag = @enumFromInt(2440), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10053 // __builtin_ve_vl_vfmkdlt_mvml
10054 .{ .tag = @enumFromInt(2441), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10055 // __builtin_ve_vl_vfmkdltnan_mvl
10056 .{ .tag = @enumFromInt(2442), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10057 // __builtin_ve_vl_vfmkdltnan_mvml
10058 .{ .tag = @enumFromInt(2443), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10059 // __builtin_ve_vl_vfmkdnan_mvl
10060 .{ .tag = @enumFromInt(2444), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10061 // __builtin_ve_vl_vfmkdnan_mvml
10062 .{ .tag = @enumFromInt(2445), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10063 // __builtin_ve_vl_vfmkdne_mvl
10064 .{ .tag = @enumFromInt(2446), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10065 // __builtin_ve_vl_vfmkdne_mvml
10066 .{ .tag = @enumFromInt(2447), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10067 // __builtin_ve_vl_vfmkdnenan_mvl
10068 .{ .tag = @enumFromInt(2448), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10069 // __builtin_ve_vl_vfmkdnenan_mvml
10070 .{ .tag = @enumFromInt(2449), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10071 // __builtin_ve_vl_vfmkdnum_mvl
10072 .{ .tag = @enumFromInt(2450), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10073 // __builtin_ve_vl_vfmkdnum_mvml
10074 .{ .tag = @enumFromInt(2451), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10075 // __builtin_ve_vl_vfmklaf_ml
10076 .{ .tag = @enumFromInt(2452), .properties = .{ .param_str = "V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10077 // __builtin_ve_vl_vfmklat_ml
10078 .{ .tag = @enumFromInt(2453), .properties = .{ .param_str = "V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10079 // __builtin_ve_vl_vfmkleq_mvl
10080 .{ .tag = @enumFromInt(2454), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10081 // __builtin_ve_vl_vfmkleq_mvml
10082 .{ .tag = @enumFromInt(2455), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10083 // __builtin_ve_vl_vfmkleqnan_mvl
10084 .{ .tag = @enumFromInt(2456), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10085 // __builtin_ve_vl_vfmkleqnan_mvml
10086 .{ .tag = @enumFromInt(2457), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10087 // __builtin_ve_vl_vfmklge_mvl
10088 .{ .tag = @enumFromInt(2458), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10089 // __builtin_ve_vl_vfmklge_mvml
10090 .{ .tag = @enumFromInt(2459), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10091 // __builtin_ve_vl_vfmklgenan_mvl
10092 .{ .tag = @enumFromInt(2460), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10093 // __builtin_ve_vl_vfmklgenan_mvml
10094 .{ .tag = @enumFromInt(2461), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10095 // __builtin_ve_vl_vfmklgt_mvl
10096 .{ .tag = @enumFromInt(2462), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10097 // __builtin_ve_vl_vfmklgt_mvml
10098 .{ .tag = @enumFromInt(2463), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10099 // __builtin_ve_vl_vfmklgtnan_mvl
10100 .{ .tag = @enumFromInt(2464), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10101 // __builtin_ve_vl_vfmklgtnan_mvml
10102 .{ .tag = @enumFromInt(2465), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10103 // __builtin_ve_vl_vfmklle_mvl
10104 .{ .tag = @enumFromInt(2466), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10105 // __builtin_ve_vl_vfmklle_mvml
10106 .{ .tag = @enumFromInt(2467), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10107 // __builtin_ve_vl_vfmkllenan_mvl
10108 .{ .tag = @enumFromInt(2468), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10109 // __builtin_ve_vl_vfmkllenan_mvml
10110 .{ .tag = @enumFromInt(2469), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10111 // __builtin_ve_vl_vfmkllt_mvl
10112 .{ .tag = @enumFromInt(2470), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10113 // __builtin_ve_vl_vfmkllt_mvml
10114 .{ .tag = @enumFromInt(2471), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10115 // __builtin_ve_vl_vfmklltnan_mvl
10116 .{ .tag = @enumFromInt(2472), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10117 // __builtin_ve_vl_vfmklltnan_mvml
10118 .{ .tag = @enumFromInt(2473), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10119 // __builtin_ve_vl_vfmklnan_mvl
10120 .{ .tag = @enumFromInt(2474), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10121 // __builtin_ve_vl_vfmklnan_mvml
10122 .{ .tag = @enumFromInt(2475), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10123 // __builtin_ve_vl_vfmklne_mvl
10124 .{ .tag = @enumFromInt(2476), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10125 // __builtin_ve_vl_vfmklne_mvml
10126 .{ .tag = @enumFromInt(2477), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10127 // __builtin_ve_vl_vfmklnenan_mvl
10128 .{ .tag = @enumFromInt(2478), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10129 // __builtin_ve_vl_vfmklnenan_mvml
10130 .{ .tag = @enumFromInt(2479), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10131 // __builtin_ve_vl_vfmklnum_mvl
10132 .{ .tag = @enumFromInt(2480), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10133 // __builtin_ve_vl_vfmklnum_mvml
10134 .{ .tag = @enumFromInt(2481), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10135 // __builtin_ve_vl_vfmkseq_mvl
10136 .{ .tag = @enumFromInt(2482), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10137 // __builtin_ve_vl_vfmkseq_mvml
10138 .{ .tag = @enumFromInt(2483), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10139 // __builtin_ve_vl_vfmkseqnan_mvl
10140 .{ .tag = @enumFromInt(2484), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10141 // __builtin_ve_vl_vfmkseqnan_mvml
10142 .{ .tag = @enumFromInt(2485), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10143 // __builtin_ve_vl_vfmksge_mvl
10144 .{ .tag = @enumFromInt(2486), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10145 // __builtin_ve_vl_vfmksge_mvml
10146 .{ .tag = @enumFromInt(2487), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10147 // __builtin_ve_vl_vfmksgenan_mvl
10148 .{ .tag = @enumFromInt(2488), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10149 // __builtin_ve_vl_vfmksgenan_mvml
10150 .{ .tag = @enumFromInt(2489), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10151 // __builtin_ve_vl_vfmksgt_mvl
10152 .{ .tag = @enumFromInt(2490), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10153 // __builtin_ve_vl_vfmksgt_mvml
10154 .{ .tag = @enumFromInt(2491), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10155 // __builtin_ve_vl_vfmksgtnan_mvl
10156 .{ .tag = @enumFromInt(2492), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10157 // __builtin_ve_vl_vfmksgtnan_mvml
10158 .{ .tag = @enumFromInt(2493), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10159 // __builtin_ve_vl_vfmksle_mvl
10160 .{ .tag = @enumFromInt(2494), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10161 // __builtin_ve_vl_vfmksle_mvml
10162 .{ .tag = @enumFromInt(2495), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10163 // __builtin_ve_vl_vfmkslenan_mvl
10164 .{ .tag = @enumFromInt(2496), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10165 // __builtin_ve_vl_vfmkslenan_mvml
10166 .{ .tag = @enumFromInt(2497), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10167 // __builtin_ve_vl_vfmkslt_mvl
10168 .{ .tag = @enumFromInt(2498), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10169 // __builtin_ve_vl_vfmkslt_mvml
10170 .{ .tag = @enumFromInt(2499), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10171 // __builtin_ve_vl_vfmksltnan_mvl
10172 .{ .tag = @enumFromInt(2500), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10173 // __builtin_ve_vl_vfmksltnan_mvml
10174 .{ .tag = @enumFromInt(2501), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10175 // __builtin_ve_vl_vfmksnan_mvl
10176 .{ .tag = @enumFromInt(2502), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10177 // __builtin_ve_vl_vfmksnan_mvml
10178 .{ .tag = @enumFromInt(2503), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10179 // __builtin_ve_vl_vfmksne_mvl
10180 .{ .tag = @enumFromInt(2504), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10181 // __builtin_ve_vl_vfmksne_mvml
10182 .{ .tag = @enumFromInt(2505), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10183 // __builtin_ve_vl_vfmksnenan_mvl
10184 .{ .tag = @enumFromInt(2506), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10185 // __builtin_ve_vl_vfmksnenan_mvml
10186 .{ .tag = @enumFromInt(2507), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10187 // __builtin_ve_vl_vfmksnum_mvl
10188 .{ .tag = @enumFromInt(2508), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10189 // __builtin_ve_vl_vfmksnum_mvml
10190 .{ .tag = @enumFromInt(2509), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10191 // __builtin_ve_vl_vfmkweq_mvl
10192 .{ .tag = @enumFromInt(2510), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10193 // __builtin_ve_vl_vfmkweq_mvml
10194 .{ .tag = @enumFromInt(2511), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10195 // __builtin_ve_vl_vfmkweqnan_mvl
10196 .{ .tag = @enumFromInt(2512), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10197 // __builtin_ve_vl_vfmkweqnan_mvml
10198 .{ .tag = @enumFromInt(2513), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10199 // __builtin_ve_vl_vfmkwge_mvl
10200 .{ .tag = @enumFromInt(2514), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10201 // __builtin_ve_vl_vfmkwge_mvml
10202 .{ .tag = @enumFromInt(2515), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10203 // __builtin_ve_vl_vfmkwgenan_mvl
10204 .{ .tag = @enumFromInt(2516), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10205 // __builtin_ve_vl_vfmkwgenan_mvml
10206 .{ .tag = @enumFromInt(2517), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10207 // __builtin_ve_vl_vfmkwgt_mvl
10208 .{ .tag = @enumFromInt(2518), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10209 // __builtin_ve_vl_vfmkwgt_mvml
10210 .{ .tag = @enumFromInt(2519), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10211 // __builtin_ve_vl_vfmkwgtnan_mvl
10212 .{ .tag = @enumFromInt(2520), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10213 // __builtin_ve_vl_vfmkwgtnan_mvml
10214 .{ .tag = @enumFromInt(2521), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10215 // __builtin_ve_vl_vfmkwle_mvl
10216 .{ .tag = @enumFromInt(2522), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10217 // __builtin_ve_vl_vfmkwle_mvml
10218 .{ .tag = @enumFromInt(2523), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10219 // __builtin_ve_vl_vfmkwlenan_mvl
10220 .{ .tag = @enumFromInt(2524), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10221 // __builtin_ve_vl_vfmkwlenan_mvml
10222 .{ .tag = @enumFromInt(2525), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10223 // __builtin_ve_vl_vfmkwlt_mvl
10224 .{ .tag = @enumFromInt(2526), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10225 // __builtin_ve_vl_vfmkwlt_mvml
10226 .{ .tag = @enumFromInt(2527), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10227 // __builtin_ve_vl_vfmkwltnan_mvl
10228 .{ .tag = @enumFromInt(2528), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10229 // __builtin_ve_vl_vfmkwltnan_mvml
10230 .{ .tag = @enumFromInt(2529), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10231 // __builtin_ve_vl_vfmkwnan_mvl
10232 .{ .tag = @enumFromInt(2530), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10233 // __builtin_ve_vl_vfmkwnan_mvml
10234 .{ .tag = @enumFromInt(2531), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10235 // __builtin_ve_vl_vfmkwne_mvl
10236 .{ .tag = @enumFromInt(2532), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10237 // __builtin_ve_vl_vfmkwne_mvml
10238 .{ .tag = @enumFromInt(2533), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10239 // __builtin_ve_vl_vfmkwnenan_mvl
10240 .{ .tag = @enumFromInt(2534), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10241 // __builtin_ve_vl_vfmkwnenan_mvml
10242 .{ .tag = @enumFromInt(2535), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10243 // __builtin_ve_vl_vfmkwnum_mvl
10244 .{ .tag = @enumFromInt(2536), .properties = .{ .param_str = "V256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10245 // __builtin_ve_vl_vfmkwnum_mvml
10246 .{ .tag = @enumFromInt(2537), .properties = .{ .param_str = "V256bV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10247 // __builtin_ve_vl_vfmsbd_vsvvl
10248 .{ .tag = @enumFromInt(2538), .properties = .{ .param_str = "V256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10249 // __builtin_ve_vl_vfmsbd_vsvvmvl
10250 .{ .tag = @enumFromInt(2539), .properties = .{ .param_str = "V256ddV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10251 // __builtin_ve_vl_vfmsbd_vsvvvl
10252 .{ .tag = @enumFromInt(2540), .properties = .{ .param_str = "V256ddV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10253 // __builtin_ve_vl_vfmsbd_vvsvl
10254 .{ .tag = @enumFromInt(2541), .properties = .{ .param_str = "V256dV256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10255 // __builtin_ve_vl_vfmsbd_vvsvmvl
10256 .{ .tag = @enumFromInt(2542), .properties = .{ .param_str = "V256dV256ddV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10257 // __builtin_ve_vl_vfmsbd_vvsvvl
10258 .{ .tag = @enumFromInt(2543), .properties = .{ .param_str = "V256dV256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10259 // __builtin_ve_vl_vfmsbd_vvvvl
10260 .{ .tag = @enumFromInt(2544), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10261 // __builtin_ve_vl_vfmsbd_vvvvmvl
10262 .{ .tag = @enumFromInt(2545), .properties = .{ .param_str = "V256dV256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10263 // __builtin_ve_vl_vfmsbd_vvvvvl
10264 .{ .tag = @enumFromInt(2546), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10265 // __builtin_ve_vl_vfmsbs_vsvvl
10266 .{ .tag = @enumFromInt(2547), .properties = .{ .param_str = "V256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10267 // __builtin_ve_vl_vfmsbs_vsvvmvl
10268 .{ .tag = @enumFromInt(2548), .properties = .{ .param_str = "V256dfV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10269 // __builtin_ve_vl_vfmsbs_vsvvvl
10270 .{ .tag = @enumFromInt(2549), .properties = .{ .param_str = "V256dfV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10271 // __builtin_ve_vl_vfmsbs_vvsvl
10272 .{ .tag = @enumFromInt(2550), .properties = .{ .param_str = "V256dV256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10273 // __builtin_ve_vl_vfmsbs_vvsvmvl
10274 .{ .tag = @enumFromInt(2551), .properties = .{ .param_str = "V256dV256dfV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10275 // __builtin_ve_vl_vfmsbs_vvsvvl
10276 .{ .tag = @enumFromInt(2552), .properties = .{ .param_str = "V256dV256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10277 // __builtin_ve_vl_vfmsbs_vvvvl
10278 .{ .tag = @enumFromInt(2553), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10279 // __builtin_ve_vl_vfmsbs_vvvvmvl
10280 .{ .tag = @enumFromInt(2554), .properties = .{ .param_str = "V256dV256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10281 // __builtin_ve_vl_vfmsbs_vvvvvl
10282 .{ .tag = @enumFromInt(2555), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10283 // __builtin_ve_vl_vfmuld_vsvl
10284 .{ .tag = @enumFromInt(2556), .properties = .{ .param_str = "V256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10285 // __builtin_ve_vl_vfmuld_vsvmvl
10286 .{ .tag = @enumFromInt(2557), .properties = .{ .param_str = "V256ddV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10287 // __builtin_ve_vl_vfmuld_vsvvl
10288 .{ .tag = @enumFromInt(2558), .properties = .{ .param_str = "V256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10289 // __builtin_ve_vl_vfmuld_vvvl
10290 .{ .tag = @enumFromInt(2559), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10291 // __builtin_ve_vl_vfmuld_vvvmvl
10292 .{ .tag = @enumFromInt(2560), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10293 // __builtin_ve_vl_vfmuld_vvvvl
10294 .{ .tag = @enumFromInt(2561), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10295 // __builtin_ve_vl_vfmuls_vsvl
10296 .{ .tag = @enumFromInt(2562), .properties = .{ .param_str = "V256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10297 // __builtin_ve_vl_vfmuls_vsvmvl
10298 .{ .tag = @enumFromInt(2563), .properties = .{ .param_str = "V256dfV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10299 // __builtin_ve_vl_vfmuls_vsvvl
10300 .{ .tag = @enumFromInt(2564), .properties = .{ .param_str = "V256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10301 // __builtin_ve_vl_vfmuls_vvvl
10302 .{ .tag = @enumFromInt(2565), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10303 // __builtin_ve_vl_vfmuls_vvvmvl
10304 .{ .tag = @enumFromInt(2566), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10305 // __builtin_ve_vl_vfmuls_vvvvl
10306 .{ .tag = @enumFromInt(2567), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10307 // __builtin_ve_vl_vfnmadd_vsvvl
10308 .{ .tag = @enumFromInt(2568), .properties = .{ .param_str = "V256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10309 // __builtin_ve_vl_vfnmadd_vsvvmvl
10310 .{ .tag = @enumFromInt(2569), .properties = .{ .param_str = "V256ddV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10311 // __builtin_ve_vl_vfnmadd_vsvvvl
10312 .{ .tag = @enumFromInt(2570), .properties = .{ .param_str = "V256ddV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10313 // __builtin_ve_vl_vfnmadd_vvsvl
10314 .{ .tag = @enumFromInt(2571), .properties = .{ .param_str = "V256dV256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10315 // __builtin_ve_vl_vfnmadd_vvsvmvl
10316 .{ .tag = @enumFromInt(2572), .properties = .{ .param_str = "V256dV256ddV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10317 // __builtin_ve_vl_vfnmadd_vvsvvl
10318 .{ .tag = @enumFromInt(2573), .properties = .{ .param_str = "V256dV256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10319 // __builtin_ve_vl_vfnmadd_vvvvl
10320 .{ .tag = @enumFromInt(2574), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10321 // __builtin_ve_vl_vfnmadd_vvvvmvl
10322 .{ .tag = @enumFromInt(2575), .properties = .{ .param_str = "V256dV256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10323 // __builtin_ve_vl_vfnmadd_vvvvvl
10324 .{ .tag = @enumFromInt(2576), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10325 // __builtin_ve_vl_vfnmads_vsvvl
10326 .{ .tag = @enumFromInt(2577), .properties = .{ .param_str = "V256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10327 // __builtin_ve_vl_vfnmads_vsvvmvl
10328 .{ .tag = @enumFromInt(2578), .properties = .{ .param_str = "V256dfV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10329 // __builtin_ve_vl_vfnmads_vsvvvl
10330 .{ .tag = @enumFromInt(2579), .properties = .{ .param_str = "V256dfV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10331 // __builtin_ve_vl_vfnmads_vvsvl
10332 .{ .tag = @enumFromInt(2580), .properties = .{ .param_str = "V256dV256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10333 // __builtin_ve_vl_vfnmads_vvsvmvl
10334 .{ .tag = @enumFromInt(2581), .properties = .{ .param_str = "V256dV256dfV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10335 // __builtin_ve_vl_vfnmads_vvsvvl
10336 .{ .tag = @enumFromInt(2582), .properties = .{ .param_str = "V256dV256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10337 // __builtin_ve_vl_vfnmads_vvvvl
10338 .{ .tag = @enumFromInt(2583), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10339 // __builtin_ve_vl_vfnmads_vvvvmvl
10340 .{ .tag = @enumFromInt(2584), .properties = .{ .param_str = "V256dV256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10341 // __builtin_ve_vl_vfnmads_vvvvvl
10342 .{ .tag = @enumFromInt(2585), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10343 // __builtin_ve_vl_vfnmsbd_vsvvl
10344 .{ .tag = @enumFromInt(2586), .properties = .{ .param_str = "V256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10345 // __builtin_ve_vl_vfnmsbd_vsvvmvl
10346 .{ .tag = @enumFromInt(2587), .properties = .{ .param_str = "V256ddV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10347 // __builtin_ve_vl_vfnmsbd_vsvvvl
10348 .{ .tag = @enumFromInt(2588), .properties = .{ .param_str = "V256ddV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10349 // __builtin_ve_vl_vfnmsbd_vvsvl
10350 .{ .tag = @enumFromInt(2589), .properties = .{ .param_str = "V256dV256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10351 // __builtin_ve_vl_vfnmsbd_vvsvmvl
10352 .{ .tag = @enumFromInt(2590), .properties = .{ .param_str = "V256dV256ddV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10353 // __builtin_ve_vl_vfnmsbd_vvsvvl
10354 .{ .tag = @enumFromInt(2591), .properties = .{ .param_str = "V256dV256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10355 // __builtin_ve_vl_vfnmsbd_vvvvl
10356 .{ .tag = @enumFromInt(2592), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10357 // __builtin_ve_vl_vfnmsbd_vvvvmvl
10358 .{ .tag = @enumFromInt(2593), .properties = .{ .param_str = "V256dV256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10359 // __builtin_ve_vl_vfnmsbd_vvvvvl
10360 .{ .tag = @enumFromInt(2594), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10361 // __builtin_ve_vl_vfnmsbs_vsvvl
10362 .{ .tag = @enumFromInt(2595), .properties = .{ .param_str = "V256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10363 // __builtin_ve_vl_vfnmsbs_vsvvmvl
10364 .{ .tag = @enumFromInt(2596), .properties = .{ .param_str = "V256dfV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10365 // __builtin_ve_vl_vfnmsbs_vsvvvl
10366 .{ .tag = @enumFromInt(2597), .properties = .{ .param_str = "V256dfV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10367 // __builtin_ve_vl_vfnmsbs_vvsvl
10368 .{ .tag = @enumFromInt(2598), .properties = .{ .param_str = "V256dV256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10369 // __builtin_ve_vl_vfnmsbs_vvsvmvl
10370 .{ .tag = @enumFromInt(2599), .properties = .{ .param_str = "V256dV256dfV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10371 // __builtin_ve_vl_vfnmsbs_vvsvvl
10372 .{ .tag = @enumFromInt(2600), .properties = .{ .param_str = "V256dV256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10373 // __builtin_ve_vl_vfnmsbs_vvvvl
10374 .{ .tag = @enumFromInt(2601), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10375 // __builtin_ve_vl_vfnmsbs_vvvvmvl
10376 .{ .tag = @enumFromInt(2602), .properties = .{ .param_str = "V256dV256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10377 // __builtin_ve_vl_vfnmsbs_vvvvvl
10378 .{ .tag = @enumFromInt(2603), .properties = .{ .param_str = "V256dV256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10379 // __builtin_ve_vl_vfrmaxdfst_vvl
10380 .{ .tag = @enumFromInt(2604), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10381 // __builtin_ve_vl_vfrmaxdfst_vvvl
10382 .{ .tag = @enumFromInt(2605), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10383 // __builtin_ve_vl_vfrmaxdlst_vvl
10384 .{ .tag = @enumFromInt(2606), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10385 // __builtin_ve_vl_vfrmaxdlst_vvvl
10386 .{ .tag = @enumFromInt(2607), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10387 // __builtin_ve_vl_vfrmaxsfst_vvl
10388 .{ .tag = @enumFromInt(2608), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10389 // __builtin_ve_vl_vfrmaxsfst_vvvl
10390 .{ .tag = @enumFromInt(2609), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10391 // __builtin_ve_vl_vfrmaxslst_vvl
10392 .{ .tag = @enumFromInt(2610), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10393 // __builtin_ve_vl_vfrmaxslst_vvvl
10394 .{ .tag = @enumFromInt(2611), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10395 // __builtin_ve_vl_vfrmindfst_vvl
10396 .{ .tag = @enumFromInt(2612), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10397 // __builtin_ve_vl_vfrmindfst_vvvl
10398 .{ .tag = @enumFromInt(2613), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10399 // __builtin_ve_vl_vfrmindlst_vvl
10400 .{ .tag = @enumFromInt(2614), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10401 // __builtin_ve_vl_vfrmindlst_vvvl
10402 .{ .tag = @enumFromInt(2615), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10403 // __builtin_ve_vl_vfrminsfst_vvl
10404 .{ .tag = @enumFromInt(2616), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10405 // __builtin_ve_vl_vfrminsfst_vvvl
10406 .{ .tag = @enumFromInt(2617), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10407 // __builtin_ve_vl_vfrminslst_vvl
10408 .{ .tag = @enumFromInt(2618), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10409 // __builtin_ve_vl_vfrminslst_vvvl
10410 .{ .tag = @enumFromInt(2619), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10411 // __builtin_ve_vl_vfsqrtd_vvl
10412 .{ .tag = @enumFromInt(2620), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10413 // __builtin_ve_vl_vfsqrtd_vvvl
10414 .{ .tag = @enumFromInt(2621), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10415 // __builtin_ve_vl_vfsqrts_vvl
10416 .{ .tag = @enumFromInt(2622), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10417 // __builtin_ve_vl_vfsqrts_vvvl
10418 .{ .tag = @enumFromInt(2623), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10419 // __builtin_ve_vl_vfsubd_vsvl
10420 .{ .tag = @enumFromInt(2624), .properties = .{ .param_str = "V256ddV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10421 // __builtin_ve_vl_vfsubd_vsvmvl
10422 .{ .tag = @enumFromInt(2625), .properties = .{ .param_str = "V256ddV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10423 // __builtin_ve_vl_vfsubd_vsvvl
10424 .{ .tag = @enumFromInt(2626), .properties = .{ .param_str = "V256ddV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10425 // __builtin_ve_vl_vfsubd_vvvl
10426 .{ .tag = @enumFromInt(2627), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10427 // __builtin_ve_vl_vfsubd_vvvmvl
10428 .{ .tag = @enumFromInt(2628), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10429 // __builtin_ve_vl_vfsubd_vvvvl
10430 .{ .tag = @enumFromInt(2629), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10431 // __builtin_ve_vl_vfsubs_vsvl
10432 .{ .tag = @enumFromInt(2630), .properties = .{ .param_str = "V256dfV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10433 // __builtin_ve_vl_vfsubs_vsvmvl
10434 .{ .tag = @enumFromInt(2631), .properties = .{ .param_str = "V256dfV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10435 // __builtin_ve_vl_vfsubs_vsvvl
10436 .{ .tag = @enumFromInt(2632), .properties = .{ .param_str = "V256dfV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10437 // __builtin_ve_vl_vfsubs_vvvl
10438 .{ .tag = @enumFromInt(2633), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10439 // __builtin_ve_vl_vfsubs_vvvmvl
10440 .{ .tag = @enumFromInt(2634), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10441 // __builtin_ve_vl_vfsubs_vvvvl
10442 .{ .tag = @enumFromInt(2635), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10443 // __builtin_ve_vl_vfsumd_vvl
10444 .{ .tag = @enumFromInt(2636), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10445 // __builtin_ve_vl_vfsumd_vvml
10446 .{ .tag = @enumFromInt(2637), .properties = .{ .param_str = "V256dV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10447 // __builtin_ve_vl_vfsums_vvl
10448 .{ .tag = @enumFromInt(2638), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10449 // __builtin_ve_vl_vfsums_vvml
10450 .{ .tag = @enumFromInt(2639), .properties = .{ .param_str = "V256dV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10451 // __builtin_ve_vl_vgt_vvssl
10452 .{ .tag = @enumFromInt(2640), .properties = .{ .param_str = "V256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10453 // __builtin_ve_vl_vgt_vvssml
10454 .{ .tag = @enumFromInt(2641), .properties = .{ .param_str = "V256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10455 // __builtin_ve_vl_vgt_vvssmvl
10456 .{ .tag = @enumFromInt(2642), .properties = .{ .param_str = "V256dV256dLUiLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10457 // __builtin_ve_vl_vgt_vvssvl
10458 .{ .tag = @enumFromInt(2643), .properties = .{ .param_str = "V256dV256dLUiLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10459 // __builtin_ve_vl_vgtlsx_vvssl
10460 .{ .tag = @enumFromInt(2644), .properties = .{ .param_str = "V256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10461 // __builtin_ve_vl_vgtlsx_vvssml
10462 .{ .tag = @enumFromInt(2645), .properties = .{ .param_str = "V256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10463 // __builtin_ve_vl_vgtlsx_vvssmvl
10464 .{ .tag = @enumFromInt(2646), .properties = .{ .param_str = "V256dV256dLUiLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10465 // __builtin_ve_vl_vgtlsx_vvssvl
10466 .{ .tag = @enumFromInt(2647), .properties = .{ .param_str = "V256dV256dLUiLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10467 // __builtin_ve_vl_vgtlsxnc_vvssl
10468 .{ .tag = @enumFromInt(2648), .properties = .{ .param_str = "V256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10469 // __builtin_ve_vl_vgtlsxnc_vvssml
10470 .{ .tag = @enumFromInt(2649), .properties = .{ .param_str = "V256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10471 // __builtin_ve_vl_vgtlsxnc_vvssmvl
10472 .{ .tag = @enumFromInt(2650), .properties = .{ .param_str = "V256dV256dLUiLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10473 // __builtin_ve_vl_vgtlsxnc_vvssvl
10474 .{ .tag = @enumFromInt(2651), .properties = .{ .param_str = "V256dV256dLUiLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10475 // __builtin_ve_vl_vgtlzx_vvssl
10476 .{ .tag = @enumFromInt(2652), .properties = .{ .param_str = "V256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10477 // __builtin_ve_vl_vgtlzx_vvssml
10478 .{ .tag = @enumFromInt(2653), .properties = .{ .param_str = "V256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10479 // __builtin_ve_vl_vgtlzx_vvssmvl
10480 .{ .tag = @enumFromInt(2654), .properties = .{ .param_str = "V256dV256dLUiLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10481 // __builtin_ve_vl_vgtlzx_vvssvl
10482 .{ .tag = @enumFromInt(2655), .properties = .{ .param_str = "V256dV256dLUiLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10483 // __builtin_ve_vl_vgtlzxnc_vvssl
10484 .{ .tag = @enumFromInt(2656), .properties = .{ .param_str = "V256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10485 // __builtin_ve_vl_vgtlzxnc_vvssml
10486 .{ .tag = @enumFromInt(2657), .properties = .{ .param_str = "V256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10487 // __builtin_ve_vl_vgtlzxnc_vvssmvl
10488 .{ .tag = @enumFromInt(2658), .properties = .{ .param_str = "V256dV256dLUiLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10489 // __builtin_ve_vl_vgtlzxnc_vvssvl
10490 .{ .tag = @enumFromInt(2659), .properties = .{ .param_str = "V256dV256dLUiLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10491 // __builtin_ve_vl_vgtnc_vvssl
10492 .{ .tag = @enumFromInt(2660), .properties = .{ .param_str = "V256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10493 // __builtin_ve_vl_vgtnc_vvssml
10494 .{ .tag = @enumFromInt(2661), .properties = .{ .param_str = "V256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10495 // __builtin_ve_vl_vgtnc_vvssmvl
10496 .{ .tag = @enumFromInt(2662), .properties = .{ .param_str = "V256dV256dLUiLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10497 // __builtin_ve_vl_vgtnc_vvssvl
10498 .{ .tag = @enumFromInt(2663), .properties = .{ .param_str = "V256dV256dLUiLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10499 // __builtin_ve_vl_vgtu_vvssl
10500 .{ .tag = @enumFromInt(2664), .properties = .{ .param_str = "V256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10501 // __builtin_ve_vl_vgtu_vvssml
10502 .{ .tag = @enumFromInt(2665), .properties = .{ .param_str = "V256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10503 // __builtin_ve_vl_vgtu_vvssmvl
10504 .{ .tag = @enumFromInt(2666), .properties = .{ .param_str = "V256dV256dLUiLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10505 // __builtin_ve_vl_vgtu_vvssvl
10506 .{ .tag = @enumFromInt(2667), .properties = .{ .param_str = "V256dV256dLUiLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10507 // __builtin_ve_vl_vgtunc_vvssl
10508 .{ .tag = @enumFromInt(2668), .properties = .{ .param_str = "V256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10509 // __builtin_ve_vl_vgtunc_vvssml
10510 .{ .tag = @enumFromInt(2669), .properties = .{ .param_str = "V256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10511 // __builtin_ve_vl_vgtunc_vvssmvl
10512 .{ .tag = @enumFromInt(2670), .properties = .{ .param_str = "V256dV256dLUiLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10513 // __builtin_ve_vl_vgtunc_vvssvl
10514 .{ .tag = @enumFromInt(2671), .properties = .{ .param_str = "V256dV256dLUiLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10515 // __builtin_ve_vl_vld2d_vssl
10516 .{ .tag = @enumFromInt(2672), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10517 // __builtin_ve_vl_vld2d_vssvl
10518 .{ .tag = @enumFromInt(2673), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10519 // __builtin_ve_vl_vld2dnc_vssl
10520 .{ .tag = @enumFromInt(2674), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10521 // __builtin_ve_vl_vld2dnc_vssvl
10522 .{ .tag = @enumFromInt(2675), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10523 // __builtin_ve_vl_vld_vssl
10524 .{ .tag = @enumFromInt(2676), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10525 // __builtin_ve_vl_vld_vssvl
10526 .{ .tag = @enumFromInt(2677), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10527 // __builtin_ve_vl_vldl2dsx_vssl
10528 .{ .tag = @enumFromInt(2678), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10529 // __builtin_ve_vl_vldl2dsx_vssvl
10530 .{ .tag = @enumFromInt(2679), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10531 // __builtin_ve_vl_vldl2dsxnc_vssl
10532 .{ .tag = @enumFromInt(2680), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10533 // __builtin_ve_vl_vldl2dsxnc_vssvl
10534 .{ .tag = @enumFromInt(2681), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10535 // __builtin_ve_vl_vldl2dzx_vssl
10536 .{ .tag = @enumFromInt(2682), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10537 // __builtin_ve_vl_vldl2dzx_vssvl
10538 .{ .tag = @enumFromInt(2683), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10539 // __builtin_ve_vl_vldl2dzxnc_vssl
10540 .{ .tag = @enumFromInt(2684), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10541 // __builtin_ve_vl_vldl2dzxnc_vssvl
10542 .{ .tag = @enumFromInt(2685), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10543 // __builtin_ve_vl_vldlsx_vssl
10544 .{ .tag = @enumFromInt(2686), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10545 // __builtin_ve_vl_vldlsx_vssvl
10546 .{ .tag = @enumFromInt(2687), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10547 // __builtin_ve_vl_vldlsxnc_vssl
10548 .{ .tag = @enumFromInt(2688), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10549 // __builtin_ve_vl_vldlsxnc_vssvl
10550 .{ .tag = @enumFromInt(2689), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10551 // __builtin_ve_vl_vldlzx_vssl
10552 .{ .tag = @enumFromInt(2690), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10553 // __builtin_ve_vl_vldlzx_vssvl
10554 .{ .tag = @enumFromInt(2691), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10555 // __builtin_ve_vl_vldlzxnc_vssl
10556 .{ .tag = @enumFromInt(2692), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10557 // __builtin_ve_vl_vldlzxnc_vssvl
10558 .{ .tag = @enumFromInt(2693), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10559 // __builtin_ve_vl_vldnc_vssl
10560 .{ .tag = @enumFromInt(2694), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10561 // __builtin_ve_vl_vldnc_vssvl
10562 .{ .tag = @enumFromInt(2695), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10563 // __builtin_ve_vl_vldu2d_vssl
10564 .{ .tag = @enumFromInt(2696), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10565 // __builtin_ve_vl_vldu2d_vssvl
10566 .{ .tag = @enumFromInt(2697), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10567 // __builtin_ve_vl_vldu2dnc_vssl
10568 .{ .tag = @enumFromInt(2698), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10569 // __builtin_ve_vl_vldu2dnc_vssvl
10570 .{ .tag = @enumFromInt(2699), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10571 // __builtin_ve_vl_vldu_vssl
10572 .{ .tag = @enumFromInt(2700), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10573 // __builtin_ve_vl_vldu_vssvl
10574 .{ .tag = @enumFromInt(2701), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10575 // __builtin_ve_vl_vldunc_vssl
10576 .{ .tag = @enumFromInt(2702), .properties = .{ .param_str = "V256dLUivC*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
10577 // __builtin_ve_vl_vldunc_vssvl
10578 .{ .tag = @enumFromInt(2703), .properties = .{ .param_str = "V256dLUivC*V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10579 // __builtin_ve_vl_vldz_vvl
10580 .{ .tag = @enumFromInt(2704), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10581 // __builtin_ve_vl_vldz_vvmvl
10582 .{ .tag = @enumFromInt(2705), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10583 // __builtin_ve_vl_vldz_vvvl
10584 .{ .tag = @enumFromInt(2706), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10585 // __builtin_ve_vl_vmaxsl_vsvl
10586 .{ .tag = @enumFromInt(2707), .properties = .{ .param_str = "V256dLiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10587 // __builtin_ve_vl_vmaxsl_vsvmvl
10588 .{ .tag = @enumFromInt(2708), .properties = .{ .param_str = "V256dLiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10589 // __builtin_ve_vl_vmaxsl_vsvvl
10590 .{ .tag = @enumFromInt(2709), .properties = .{ .param_str = "V256dLiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10591 // __builtin_ve_vl_vmaxsl_vvvl
10592 .{ .tag = @enumFromInt(2710), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10593 // __builtin_ve_vl_vmaxsl_vvvmvl
10594 .{ .tag = @enumFromInt(2711), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10595 // __builtin_ve_vl_vmaxsl_vvvvl
10596 .{ .tag = @enumFromInt(2712), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10597 // __builtin_ve_vl_vmaxswsx_vsvl
10598 .{ .tag = @enumFromInt(2713), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10599 // __builtin_ve_vl_vmaxswsx_vsvmvl
10600 .{ .tag = @enumFromInt(2714), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10601 // __builtin_ve_vl_vmaxswsx_vsvvl
10602 .{ .tag = @enumFromInt(2715), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10603 // __builtin_ve_vl_vmaxswsx_vvvl
10604 .{ .tag = @enumFromInt(2716), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10605 // __builtin_ve_vl_vmaxswsx_vvvmvl
10606 .{ .tag = @enumFromInt(2717), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10607 // __builtin_ve_vl_vmaxswsx_vvvvl
10608 .{ .tag = @enumFromInt(2718), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10609 // __builtin_ve_vl_vmaxswzx_vsvl
10610 .{ .tag = @enumFromInt(2719), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10611 // __builtin_ve_vl_vmaxswzx_vsvmvl
10612 .{ .tag = @enumFromInt(2720), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10613 // __builtin_ve_vl_vmaxswzx_vsvvl
10614 .{ .tag = @enumFromInt(2721), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10615 // __builtin_ve_vl_vmaxswzx_vvvl
10616 .{ .tag = @enumFromInt(2722), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10617 // __builtin_ve_vl_vmaxswzx_vvvmvl
10618 .{ .tag = @enumFromInt(2723), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10619 // __builtin_ve_vl_vmaxswzx_vvvvl
10620 .{ .tag = @enumFromInt(2724), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10621 // __builtin_ve_vl_vminsl_vsvl
10622 .{ .tag = @enumFromInt(2725), .properties = .{ .param_str = "V256dLiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10623 // __builtin_ve_vl_vminsl_vsvmvl
10624 .{ .tag = @enumFromInt(2726), .properties = .{ .param_str = "V256dLiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10625 // __builtin_ve_vl_vminsl_vsvvl
10626 .{ .tag = @enumFromInt(2727), .properties = .{ .param_str = "V256dLiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10627 // __builtin_ve_vl_vminsl_vvvl
10628 .{ .tag = @enumFromInt(2728), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10629 // __builtin_ve_vl_vminsl_vvvmvl
10630 .{ .tag = @enumFromInt(2729), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10631 // __builtin_ve_vl_vminsl_vvvvl
10632 .{ .tag = @enumFromInt(2730), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10633 // __builtin_ve_vl_vminswsx_vsvl
10634 .{ .tag = @enumFromInt(2731), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10635 // __builtin_ve_vl_vminswsx_vsvmvl
10636 .{ .tag = @enumFromInt(2732), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10637 // __builtin_ve_vl_vminswsx_vsvvl
10638 .{ .tag = @enumFromInt(2733), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10639 // __builtin_ve_vl_vminswsx_vvvl
10640 .{ .tag = @enumFromInt(2734), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10641 // __builtin_ve_vl_vminswsx_vvvmvl
10642 .{ .tag = @enumFromInt(2735), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10643 // __builtin_ve_vl_vminswsx_vvvvl
10644 .{ .tag = @enumFromInt(2736), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10645 // __builtin_ve_vl_vminswzx_vsvl
10646 .{ .tag = @enumFromInt(2737), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10647 // __builtin_ve_vl_vminswzx_vsvmvl
10648 .{ .tag = @enumFromInt(2738), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10649 // __builtin_ve_vl_vminswzx_vsvvl
10650 .{ .tag = @enumFromInt(2739), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10651 // __builtin_ve_vl_vminswzx_vvvl
10652 .{ .tag = @enumFromInt(2740), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10653 // __builtin_ve_vl_vminswzx_vvvmvl
10654 .{ .tag = @enumFromInt(2741), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10655 // __builtin_ve_vl_vminswzx_vvvvl
10656 .{ .tag = @enumFromInt(2742), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10657 // __builtin_ve_vl_vmrg_vsvml
10658 .{ .tag = @enumFromInt(2743), .properties = .{ .param_str = "V256dLUiV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10659 // __builtin_ve_vl_vmrg_vsvmvl
10660 .{ .tag = @enumFromInt(2744), .properties = .{ .param_str = "V256dLUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10661 // __builtin_ve_vl_vmrg_vvvml
10662 .{ .tag = @enumFromInt(2745), .properties = .{ .param_str = "V256dV256dV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10663 // __builtin_ve_vl_vmrg_vvvmvl
10664 .{ .tag = @enumFromInt(2746), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10665 // __builtin_ve_vl_vmrgw_vsvMl
10666 .{ .tag = @enumFromInt(2747), .properties = .{ .param_str = "V256dUiV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10667 // __builtin_ve_vl_vmrgw_vsvMvl
10668 .{ .tag = @enumFromInt(2748), .properties = .{ .param_str = "V256dUiV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10669 // __builtin_ve_vl_vmrgw_vvvMl
10670 .{ .tag = @enumFromInt(2749), .properties = .{ .param_str = "V256dV256dV256dV512bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10671 // __builtin_ve_vl_vmrgw_vvvMvl
10672 .{ .tag = @enumFromInt(2750), .properties = .{ .param_str = "V256dV256dV256dV512bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10673 // __builtin_ve_vl_vmulsl_vsvl
10674 .{ .tag = @enumFromInt(2751), .properties = .{ .param_str = "V256dLiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10675 // __builtin_ve_vl_vmulsl_vsvmvl
10676 .{ .tag = @enumFromInt(2752), .properties = .{ .param_str = "V256dLiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10677 // __builtin_ve_vl_vmulsl_vsvvl
10678 .{ .tag = @enumFromInt(2753), .properties = .{ .param_str = "V256dLiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10679 // __builtin_ve_vl_vmulsl_vvvl
10680 .{ .tag = @enumFromInt(2754), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10681 // __builtin_ve_vl_vmulsl_vvvmvl
10682 .{ .tag = @enumFromInt(2755), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10683 // __builtin_ve_vl_vmulsl_vvvvl
10684 .{ .tag = @enumFromInt(2756), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10685 // __builtin_ve_vl_vmulslw_vsvl
10686 .{ .tag = @enumFromInt(2757), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10687 // __builtin_ve_vl_vmulslw_vsvvl
10688 .{ .tag = @enumFromInt(2758), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10689 // __builtin_ve_vl_vmulslw_vvvl
10690 .{ .tag = @enumFromInt(2759), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10691 // __builtin_ve_vl_vmulslw_vvvvl
10692 .{ .tag = @enumFromInt(2760), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10693 // __builtin_ve_vl_vmulswsx_vsvl
10694 .{ .tag = @enumFromInt(2761), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10695 // __builtin_ve_vl_vmulswsx_vsvmvl
10696 .{ .tag = @enumFromInt(2762), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10697 // __builtin_ve_vl_vmulswsx_vsvvl
10698 .{ .tag = @enumFromInt(2763), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10699 // __builtin_ve_vl_vmulswsx_vvvl
10700 .{ .tag = @enumFromInt(2764), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10701 // __builtin_ve_vl_vmulswsx_vvvmvl
10702 .{ .tag = @enumFromInt(2765), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10703 // __builtin_ve_vl_vmulswsx_vvvvl
10704 .{ .tag = @enumFromInt(2766), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10705 // __builtin_ve_vl_vmulswzx_vsvl
10706 .{ .tag = @enumFromInt(2767), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10707 // __builtin_ve_vl_vmulswzx_vsvmvl
10708 .{ .tag = @enumFromInt(2768), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10709 // __builtin_ve_vl_vmulswzx_vsvvl
10710 .{ .tag = @enumFromInt(2769), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10711 // __builtin_ve_vl_vmulswzx_vvvl
10712 .{ .tag = @enumFromInt(2770), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10713 // __builtin_ve_vl_vmulswzx_vvvmvl
10714 .{ .tag = @enumFromInt(2771), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10715 // __builtin_ve_vl_vmulswzx_vvvvl
10716 .{ .tag = @enumFromInt(2772), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10717 // __builtin_ve_vl_vmulul_vsvl
10718 .{ .tag = @enumFromInt(2773), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10719 // __builtin_ve_vl_vmulul_vsvmvl
10720 .{ .tag = @enumFromInt(2774), .properties = .{ .param_str = "V256dLUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10721 // __builtin_ve_vl_vmulul_vsvvl
10722 .{ .tag = @enumFromInt(2775), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10723 // __builtin_ve_vl_vmulul_vvvl
10724 .{ .tag = @enumFromInt(2776), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10725 // __builtin_ve_vl_vmulul_vvvmvl
10726 .{ .tag = @enumFromInt(2777), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10727 // __builtin_ve_vl_vmulul_vvvvl
10728 .{ .tag = @enumFromInt(2778), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10729 // __builtin_ve_vl_vmuluw_vsvl
10730 .{ .tag = @enumFromInt(2779), .properties = .{ .param_str = "V256dUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10731 // __builtin_ve_vl_vmuluw_vsvmvl
10732 .{ .tag = @enumFromInt(2780), .properties = .{ .param_str = "V256dUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10733 // __builtin_ve_vl_vmuluw_vsvvl
10734 .{ .tag = @enumFromInt(2781), .properties = .{ .param_str = "V256dUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10735 // __builtin_ve_vl_vmuluw_vvvl
10736 .{ .tag = @enumFromInt(2782), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10737 // __builtin_ve_vl_vmuluw_vvvmvl
10738 .{ .tag = @enumFromInt(2783), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10739 // __builtin_ve_vl_vmuluw_vvvvl
10740 .{ .tag = @enumFromInt(2784), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10741 // __builtin_ve_vl_vmv_vsvl
10742 .{ .tag = @enumFromInt(2785), .properties = .{ .param_str = "V256dUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10743 // __builtin_ve_vl_vmv_vsvmvl
10744 .{ .tag = @enumFromInt(2786), .properties = .{ .param_str = "V256dUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10745 // __builtin_ve_vl_vmv_vsvvl
10746 .{ .tag = @enumFromInt(2787), .properties = .{ .param_str = "V256dUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10747 // __builtin_ve_vl_vor_vsvl
10748 .{ .tag = @enumFromInt(2788), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10749 // __builtin_ve_vl_vor_vsvmvl
10750 .{ .tag = @enumFromInt(2789), .properties = .{ .param_str = "V256dLUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10751 // __builtin_ve_vl_vor_vsvvl
10752 .{ .tag = @enumFromInt(2790), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10753 // __builtin_ve_vl_vor_vvvl
10754 .{ .tag = @enumFromInt(2791), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10755 // __builtin_ve_vl_vor_vvvmvl
10756 .{ .tag = @enumFromInt(2792), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10757 // __builtin_ve_vl_vor_vvvvl
10758 .{ .tag = @enumFromInt(2793), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10759 // __builtin_ve_vl_vpcnt_vvl
10760 .{ .tag = @enumFromInt(2794), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10761 // __builtin_ve_vl_vpcnt_vvmvl
10762 .{ .tag = @enumFromInt(2795), .properties = .{ .param_str = "V256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10763 // __builtin_ve_vl_vpcnt_vvvl
10764 .{ .tag = @enumFromInt(2796), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10765 // __builtin_ve_vl_vrand_vvl
10766 .{ .tag = @enumFromInt(2797), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10767 // __builtin_ve_vl_vrand_vvml
10768 .{ .tag = @enumFromInt(2798), .properties = .{ .param_str = "V256dV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10769 // __builtin_ve_vl_vrcpd_vvl
10770 .{ .tag = @enumFromInt(2799), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10771 // __builtin_ve_vl_vrcpd_vvvl
10772 .{ .tag = @enumFromInt(2800), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10773 // __builtin_ve_vl_vrcps_vvl
10774 .{ .tag = @enumFromInt(2801), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10775 // __builtin_ve_vl_vrcps_vvvl
10776 .{ .tag = @enumFromInt(2802), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10777 // __builtin_ve_vl_vrmaxslfst_vvl
10778 .{ .tag = @enumFromInt(2803), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10779 // __builtin_ve_vl_vrmaxslfst_vvvl
10780 .{ .tag = @enumFromInt(2804), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10781 // __builtin_ve_vl_vrmaxsllst_vvl
10782 .{ .tag = @enumFromInt(2805), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10783 // __builtin_ve_vl_vrmaxsllst_vvvl
10784 .{ .tag = @enumFromInt(2806), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10785 // __builtin_ve_vl_vrmaxswfstsx_vvl
10786 .{ .tag = @enumFromInt(2807), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10787 // __builtin_ve_vl_vrmaxswfstsx_vvvl
10788 .{ .tag = @enumFromInt(2808), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10789 // __builtin_ve_vl_vrmaxswfstzx_vvl
10790 .{ .tag = @enumFromInt(2809), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10791 // __builtin_ve_vl_vrmaxswfstzx_vvvl
10792 .{ .tag = @enumFromInt(2810), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10793 // __builtin_ve_vl_vrmaxswlstsx_vvl
10794 .{ .tag = @enumFromInt(2811), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10795 // __builtin_ve_vl_vrmaxswlstsx_vvvl
10796 .{ .tag = @enumFromInt(2812), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10797 // __builtin_ve_vl_vrmaxswlstzx_vvl
10798 .{ .tag = @enumFromInt(2813), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10799 // __builtin_ve_vl_vrmaxswlstzx_vvvl
10800 .{ .tag = @enumFromInt(2814), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10801 // __builtin_ve_vl_vrminslfst_vvl
10802 .{ .tag = @enumFromInt(2815), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10803 // __builtin_ve_vl_vrminslfst_vvvl
10804 .{ .tag = @enumFromInt(2816), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10805 // __builtin_ve_vl_vrminsllst_vvl
10806 .{ .tag = @enumFromInt(2817), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10807 // __builtin_ve_vl_vrminsllst_vvvl
10808 .{ .tag = @enumFromInt(2818), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10809 // __builtin_ve_vl_vrminswfstsx_vvl
10810 .{ .tag = @enumFromInt(2819), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10811 // __builtin_ve_vl_vrminswfstsx_vvvl
10812 .{ .tag = @enumFromInt(2820), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10813 // __builtin_ve_vl_vrminswfstzx_vvl
10814 .{ .tag = @enumFromInt(2821), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10815 // __builtin_ve_vl_vrminswfstzx_vvvl
10816 .{ .tag = @enumFromInt(2822), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10817 // __builtin_ve_vl_vrminswlstsx_vvl
10818 .{ .tag = @enumFromInt(2823), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10819 // __builtin_ve_vl_vrminswlstsx_vvvl
10820 .{ .tag = @enumFromInt(2824), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10821 // __builtin_ve_vl_vrminswlstzx_vvl
10822 .{ .tag = @enumFromInt(2825), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10823 // __builtin_ve_vl_vrminswlstzx_vvvl
10824 .{ .tag = @enumFromInt(2826), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10825 // __builtin_ve_vl_vror_vvl
10826 .{ .tag = @enumFromInt(2827), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10827 // __builtin_ve_vl_vror_vvml
10828 .{ .tag = @enumFromInt(2828), .properties = .{ .param_str = "V256dV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10829 // __builtin_ve_vl_vrsqrtd_vvl
10830 .{ .tag = @enumFromInt(2829), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10831 // __builtin_ve_vl_vrsqrtd_vvvl
10832 .{ .tag = @enumFromInt(2830), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10833 // __builtin_ve_vl_vrsqrtdnex_vvl
10834 .{ .tag = @enumFromInt(2831), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10835 // __builtin_ve_vl_vrsqrtdnex_vvvl
10836 .{ .tag = @enumFromInt(2832), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10837 // __builtin_ve_vl_vrsqrts_vvl
10838 .{ .tag = @enumFromInt(2833), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10839 // __builtin_ve_vl_vrsqrts_vvvl
10840 .{ .tag = @enumFromInt(2834), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10841 // __builtin_ve_vl_vrsqrtsnex_vvl
10842 .{ .tag = @enumFromInt(2835), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10843 // __builtin_ve_vl_vrsqrtsnex_vvvl
10844 .{ .tag = @enumFromInt(2836), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10845 // __builtin_ve_vl_vrxor_vvl
10846 .{ .tag = @enumFromInt(2837), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10847 // __builtin_ve_vl_vrxor_vvml
10848 .{ .tag = @enumFromInt(2838), .properties = .{ .param_str = "V256dV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10849 // __builtin_ve_vl_vsc_vvssl
10850 .{ .tag = @enumFromInt(2839), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10851 // __builtin_ve_vl_vsc_vvssml
10852 .{ .tag = @enumFromInt(2840), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10853 // __builtin_ve_vl_vscl_vvssl
10854 .{ .tag = @enumFromInt(2841), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10855 // __builtin_ve_vl_vscl_vvssml
10856 .{ .tag = @enumFromInt(2842), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10857 // __builtin_ve_vl_vsclnc_vvssl
10858 .{ .tag = @enumFromInt(2843), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10859 // __builtin_ve_vl_vsclnc_vvssml
10860 .{ .tag = @enumFromInt(2844), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10861 // __builtin_ve_vl_vsclncot_vvssl
10862 .{ .tag = @enumFromInt(2845), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10863 // __builtin_ve_vl_vsclncot_vvssml
10864 .{ .tag = @enumFromInt(2846), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10865 // __builtin_ve_vl_vsclot_vvssl
10866 .{ .tag = @enumFromInt(2847), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10867 // __builtin_ve_vl_vsclot_vvssml
10868 .{ .tag = @enumFromInt(2848), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10869 // __builtin_ve_vl_vscnc_vvssl
10870 .{ .tag = @enumFromInt(2849), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10871 // __builtin_ve_vl_vscnc_vvssml
10872 .{ .tag = @enumFromInt(2850), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10873 // __builtin_ve_vl_vscncot_vvssl
10874 .{ .tag = @enumFromInt(2851), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10875 // __builtin_ve_vl_vscncot_vvssml
10876 .{ .tag = @enumFromInt(2852), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10877 // __builtin_ve_vl_vscot_vvssl
10878 .{ .tag = @enumFromInt(2853), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10879 // __builtin_ve_vl_vscot_vvssml
10880 .{ .tag = @enumFromInt(2854), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10881 // __builtin_ve_vl_vscu_vvssl
10882 .{ .tag = @enumFromInt(2855), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10883 // __builtin_ve_vl_vscu_vvssml
10884 .{ .tag = @enumFromInt(2856), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10885 // __builtin_ve_vl_vscunc_vvssl
10886 .{ .tag = @enumFromInt(2857), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10887 // __builtin_ve_vl_vscunc_vvssml
10888 .{ .tag = @enumFromInt(2858), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10889 // __builtin_ve_vl_vscuncot_vvssl
10890 .{ .tag = @enumFromInt(2859), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10891 // __builtin_ve_vl_vscuncot_vvssml
10892 .{ .tag = @enumFromInt(2860), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10893 // __builtin_ve_vl_vscuot_vvssl
10894 .{ .tag = @enumFromInt(2861), .properties = .{ .param_str = "vV256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10895 // __builtin_ve_vl_vscuot_vvssml
10896 .{ .tag = @enumFromInt(2862), .properties = .{ .param_str = "vV256dV256dLUiLUiV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10897 // __builtin_ve_vl_vseq_vl
10898 .{ .tag = @enumFromInt(2863), .properties = .{ .param_str = "V256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10899 // __builtin_ve_vl_vseq_vvl
10900 .{ .tag = @enumFromInt(2864), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10901 // __builtin_ve_vl_vsfa_vvssl
10902 .{ .tag = @enumFromInt(2865), .properties = .{ .param_str = "V256dV256dLUiLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10903 // __builtin_ve_vl_vsfa_vvssmvl
10904 .{ .tag = @enumFromInt(2866), .properties = .{ .param_str = "V256dV256dLUiLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10905 // __builtin_ve_vl_vsfa_vvssvl
10906 .{ .tag = @enumFromInt(2867), .properties = .{ .param_str = "V256dV256dLUiLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10907 // __builtin_ve_vl_vshf_vvvsl
10908 .{ .tag = @enumFromInt(2868), .properties = .{ .param_str = "V256dV256dV256dLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10909 // __builtin_ve_vl_vshf_vvvsvl
10910 .{ .tag = @enumFromInt(2869), .properties = .{ .param_str = "V256dV256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10911 // __builtin_ve_vl_vslal_vvsl
10912 .{ .tag = @enumFromInt(2870), .properties = .{ .param_str = "V256dV256dLiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10913 // __builtin_ve_vl_vslal_vvsmvl
10914 .{ .tag = @enumFromInt(2871), .properties = .{ .param_str = "V256dV256dLiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10915 // __builtin_ve_vl_vslal_vvsvl
10916 .{ .tag = @enumFromInt(2872), .properties = .{ .param_str = "V256dV256dLiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10917 // __builtin_ve_vl_vslal_vvvl
10918 .{ .tag = @enumFromInt(2873), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10919 // __builtin_ve_vl_vslal_vvvmvl
10920 .{ .tag = @enumFromInt(2874), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10921 // __builtin_ve_vl_vslal_vvvvl
10922 .{ .tag = @enumFromInt(2875), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10923 // __builtin_ve_vl_vslawsx_vvsl
10924 .{ .tag = @enumFromInt(2876), .properties = .{ .param_str = "V256dV256diUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10925 // __builtin_ve_vl_vslawsx_vvsmvl
10926 .{ .tag = @enumFromInt(2877), .properties = .{ .param_str = "V256dV256diV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10927 // __builtin_ve_vl_vslawsx_vvsvl
10928 .{ .tag = @enumFromInt(2878), .properties = .{ .param_str = "V256dV256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10929 // __builtin_ve_vl_vslawsx_vvvl
10930 .{ .tag = @enumFromInt(2879), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10931 // __builtin_ve_vl_vslawsx_vvvmvl
10932 .{ .tag = @enumFromInt(2880), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10933 // __builtin_ve_vl_vslawsx_vvvvl
10934 .{ .tag = @enumFromInt(2881), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10935 // __builtin_ve_vl_vslawzx_vvsl
10936 .{ .tag = @enumFromInt(2882), .properties = .{ .param_str = "V256dV256diUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10937 // __builtin_ve_vl_vslawzx_vvsmvl
10938 .{ .tag = @enumFromInt(2883), .properties = .{ .param_str = "V256dV256diV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10939 // __builtin_ve_vl_vslawzx_vvsvl
10940 .{ .tag = @enumFromInt(2884), .properties = .{ .param_str = "V256dV256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10941 // __builtin_ve_vl_vslawzx_vvvl
10942 .{ .tag = @enumFromInt(2885), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10943 // __builtin_ve_vl_vslawzx_vvvmvl
10944 .{ .tag = @enumFromInt(2886), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10945 // __builtin_ve_vl_vslawzx_vvvvl
10946 .{ .tag = @enumFromInt(2887), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10947 // __builtin_ve_vl_vsll_vvsl
10948 .{ .tag = @enumFromInt(2888), .properties = .{ .param_str = "V256dV256dLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10949 // __builtin_ve_vl_vsll_vvsmvl
10950 .{ .tag = @enumFromInt(2889), .properties = .{ .param_str = "V256dV256dLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10951 // __builtin_ve_vl_vsll_vvsvl
10952 .{ .tag = @enumFromInt(2890), .properties = .{ .param_str = "V256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10953 // __builtin_ve_vl_vsll_vvvl
10954 .{ .tag = @enumFromInt(2891), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10955 // __builtin_ve_vl_vsll_vvvmvl
10956 .{ .tag = @enumFromInt(2892), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10957 // __builtin_ve_vl_vsll_vvvvl
10958 .{ .tag = @enumFromInt(2893), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10959 // __builtin_ve_vl_vsral_vvsl
10960 .{ .tag = @enumFromInt(2894), .properties = .{ .param_str = "V256dV256dLiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10961 // __builtin_ve_vl_vsral_vvsmvl
10962 .{ .tag = @enumFromInt(2895), .properties = .{ .param_str = "V256dV256dLiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10963 // __builtin_ve_vl_vsral_vvsvl
10964 .{ .tag = @enumFromInt(2896), .properties = .{ .param_str = "V256dV256dLiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10965 // __builtin_ve_vl_vsral_vvvl
10966 .{ .tag = @enumFromInt(2897), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10967 // __builtin_ve_vl_vsral_vvvmvl
10968 .{ .tag = @enumFromInt(2898), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10969 // __builtin_ve_vl_vsral_vvvvl
10970 .{ .tag = @enumFromInt(2899), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10971 // __builtin_ve_vl_vsrawsx_vvsl
10972 .{ .tag = @enumFromInt(2900), .properties = .{ .param_str = "V256dV256diUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10973 // __builtin_ve_vl_vsrawsx_vvsmvl
10974 .{ .tag = @enumFromInt(2901), .properties = .{ .param_str = "V256dV256diV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10975 // __builtin_ve_vl_vsrawsx_vvsvl
10976 .{ .tag = @enumFromInt(2902), .properties = .{ .param_str = "V256dV256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10977 // __builtin_ve_vl_vsrawsx_vvvl
10978 .{ .tag = @enumFromInt(2903), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10979 // __builtin_ve_vl_vsrawsx_vvvmvl
10980 .{ .tag = @enumFromInt(2904), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10981 // __builtin_ve_vl_vsrawsx_vvvvl
10982 .{ .tag = @enumFromInt(2905), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10983 // __builtin_ve_vl_vsrawzx_vvsl
10984 .{ .tag = @enumFromInt(2906), .properties = .{ .param_str = "V256dV256diUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10985 // __builtin_ve_vl_vsrawzx_vvsmvl
10986 .{ .tag = @enumFromInt(2907), .properties = .{ .param_str = "V256dV256diV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10987 // __builtin_ve_vl_vsrawzx_vvsvl
10988 .{ .tag = @enumFromInt(2908), .properties = .{ .param_str = "V256dV256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10989 // __builtin_ve_vl_vsrawzx_vvvl
10990 .{ .tag = @enumFromInt(2909), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10991 // __builtin_ve_vl_vsrawzx_vvvmvl
10992 .{ .tag = @enumFromInt(2910), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10993 // __builtin_ve_vl_vsrawzx_vvvvl
10994 .{ .tag = @enumFromInt(2911), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10995 // __builtin_ve_vl_vsrl_vvsl
10996 .{ .tag = @enumFromInt(2912), .properties = .{ .param_str = "V256dV256dLUiUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10997 // __builtin_ve_vl_vsrl_vvsmvl
10998 .{ .tag = @enumFromInt(2913), .properties = .{ .param_str = "V256dV256dLUiV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
10999 // __builtin_ve_vl_vsrl_vvsvl
11000 .{ .tag = @enumFromInt(2914), .properties = .{ .param_str = "V256dV256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11001 // __builtin_ve_vl_vsrl_vvvl
11002 .{ .tag = @enumFromInt(2915), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11003 // __builtin_ve_vl_vsrl_vvvmvl
11004 .{ .tag = @enumFromInt(2916), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11005 // __builtin_ve_vl_vsrl_vvvvl
11006 .{ .tag = @enumFromInt(2917), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11007 // __builtin_ve_vl_vst2d_vssl
11008 .{ .tag = @enumFromInt(2918), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11009 // __builtin_ve_vl_vst2d_vssml
11010 .{ .tag = @enumFromInt(2919), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11011 // __builtin_ve_vl_vst2dnc_vssl
11012 .{ .tag = @enumFromInt(2920), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11013 // __builtin_ve_vl_vst2dnc_vssml
11014 .{ .tag = @enumFromInt(2921), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11015 // __builtin_ve_vl_vst2dncot_vssl
11016 .{ .tag = @enumFromInt(2922), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11017 // __builtin_ve_vl_vst2dncot_vssml
11018 .{ .tag = @enumFromInt(2923), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11019 // __builtin_ve_vl_vst2dot_vssl
11020 .{ .tag = @enumFromInt(2924), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11021 // __builtin_ve_vl_vst2dot_vssml
11022 .{ .tag = @enumFromInt(2925), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11023 // __builtin_ve_vl_vst_vssl
11024 .{ .tag = @enumFromInt(2926), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11025 // __builtin_ve_vl_vst_vssml
11026 .{ .tag = @enumFromInt(2927), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11027 // __builtin_ve_vl_vstl2d_vssl
11028 .{ .tag = @enumFromInt(2928), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11029 // __builtin_ve_vl_vstl2d_vssml
11030 .{ .tag = @enumFromInt(2929), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11031 // __builtin_ve_vl_vstl2dnc_vssl
11032 .{ .tag = @enumFromInt(2930), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11033 // __builtin_ve_vl_vstl2dnc_vssml
11034 .{ .tag = @enumFromInt(2931), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11035 // __builtin_ve_vl_vstl2dncot_vssl
11036 .{ .tag = @enumFromInt(2932), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11037 // __builtin_ve_vl_vstl2dncot_vssml
11038 .{ .tag = @enumFromInt(2933), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11039 // __builtin_ve_vl_vstl2dot_vssl
11040 .{ .tag = @enumFromInt(2934), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11041 // __builtin_ve_vl_vstl2dot_vssml
11042 .{ .tag = @enumFromInt(2935), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11043 // __builtin_ve_vl_vstl_vssl
11044 .{ .tag = @enumFromInt(2936), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11045 // __builtin_ve_vl_vstl_vssml
11046 .{ .tag = @enumFromInt(2937), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11047 // __builtin_ve_vl_vstlnc_vssl
11048 .{ .tag = @enumFromInt(2938), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11049 // __builtin_ve_vl_vstlnc_vssml
11050 .{ .tag = @enumFromInt(2939), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11051 // __builtin_ve_vl_vstlncot_vssl
11052 .{ .tag = @enumFromInt(2940), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11053 // __builtin_ve_vl_vstlncot_vssml
11054 .{ .tag = @enumFromInt(2941), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11055 // __builtin_ve_vl_vstlot_vssl
11056 .{ .tag = @enumFromInt(2942), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11057 // __builtin_ve_vl_vstlot_vssml
11058 .{ .tag = @enumFromInt(2943), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11059 // __builtin_ve_vl_vstnc_vssl
11060 .{ .tag = @enumFromInt(2944), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11061 // __builtin_ve_vl_vstnc_vssml
11062 .{ .tag = @enumFromInt(2945), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11063 // __builtin_ve_vl_vstncot_vssl
11064 .{ .tag = @enumFromInt(2946), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11065 // __builtin_ve_vl_vstncot_vssml
11066 .{ .tag = @enumFromInt(2947), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11067 // __builtin_ve_vl_vstot_vssl
11068 .{ .tag = @enumFromInt(2948), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11069 // __builtin_ve_vl_vstot_vssml
11070 .{ .tag = @enumFromInt(2949), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11071 // __builtin_ve_vl_vstu2d_vssl
11072 .{ .tag = @enumFromInt(2950), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11073 // __builtin_ve_vl_vstu2d_vssml
11074 .{ .tag = @enumFromInt(2951), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11075 // __builtin_ve_vl_vstu2dnc_vssl
11076 .{ .tag = @enumFromInt(2952), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11077 // __builtin_ve_vl_vstu2dnc_vssml
11078 .{ .tag = @enumFromInt(2953), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11079 // __builtin_ve_vl_vstu2dncot_vssl
11080 .{ .tag = @enumFromInt(2954), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11081 // __builtin_ve_vl_vstu2dncot_vssml
11082 .{ .tag = @enumFromInt(2955), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11083 // __builtin_ve_vl_vstu2dot_vssl
11084 .{ .tag = @enumFromInt(2956), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11085 // __builtin_ve_vl_vstu2dot_vssml
11086 .{ .tag = @enumFromInt(2957), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11087 // __builtin_ve_vl_vstu_vssl
11088 .{ .tag = @enumFromInt(2958), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11089 // __builtin_ve_vl_vstu_vssml
11090 .{ .tag = @enumFromInt(2959), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11091 // __builtin_ve_vl_vstunc_vssl
11092 .{ .tag = @enumFromInt(2960), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11093 // __builtin_ve_vl_vstunc_vssml
11094 .{ .tag = @enumFromInt(2961), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11095 // __builtin_ve_vl_vstuncot_vssl
11096 .{ .tag = @enumFromInt(2962), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11097 // __builtin_ve_vl_vstuncot_vssml
11098 .{ .tag = @enumFromInt(2963), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11099 // __builtin_ve_vl_vstuot_vssl
11100 .{ .tag = @enumFromInt(2964), .properties = .{ .param_str = "vV256dLUiv*Ui", .target_set = TargetSet.initOne(.vevl_gen) } },
11101 // __builtin_ve_vl_vstuot_vssml
11102 .{ .tag = @enumFromInt(2965), .properties = .{ .param_str = "vV256dLUiv*V256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11103 // __builtin_ve_vl_vsubsl_vsvl
11104 .{ .tag = @enumFromInt(2966), .properties = .{ .param_str = "V256dLiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11105 // __builtin_ve_vl_vsubsl_vsvmvl
11106 .{ .tag = @enumFromInt(2967), .properties = .{ .param_str = "V256dLiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11107 // __builtin_ve_vl_vsubsl_vsvvl
11108 .{ .tag = @enumFromInt(2968), .properties = .{ .param_str = "V256dLiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11109 // __builtin_ve_vl_vsubsl_vvvl
11110 .{ .tag = @enumFromInt(2969), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11111 // __builtin_ve_vl_vsubsl_vvvmvl
11112 .{ .tag = @enumFromInt(2970), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11113 // __builtin_ve_vl_vsubsl_vvvvl
11114 .{ .tag = @enumFromInt(2971), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11115 // __builtin_ve_vl_vsubswsx_vsvl
11116 .{ .tag = @enumFromInt(2972), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11117 // __builtin_ve_vl_vsubswsx_vsvmvl
11118 .{ .tag = @enumFromInt(2973), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11119 // __builtin_ve_vl_vsubswsx_vsvvl
11120 .{ .tag = @enumFromInt(2974), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11121 // __builtin_ve_vl_vsubswsx_vvvl
11122 .{ .tag = @enumFromInt(2975), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11123 // __builtin_ve_vl_vsubswsx_vvvmvl
11124 .{ .tag = @enumFromInt(2976), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11125 // __builtin_ve_vl_vsubswsx_vvvvl
11126 .{ .tag = @enumFromInt(2977), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11127 // __builtin_ve_vl_vsubswzx_vsvl
11128 .{ .tag = @enumFromInt(2978), .properties = .{ .param_str = "V256diV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11129 // __builtin_ve_vl_vsubswzx_vsvmvl
11130 .{ .tag = @enumFromInt(2979), .properties = .{ .param_str = "V256diV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11131 // __builtin_ve_vl_vsubswzx_vsvvl
11132 .{ .tag = @enumFromInt(2980), .properties = .{ .param_str = "V256diV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11133 // __builtin_ve_vl_vsubswzx_vvvl
11134 .{ .tag = @enumFromInt(2981), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11135 // __builtin_ve_vl_vsubswzx_vvvmvl
11136 .{ .tag = @enumFromInt(2982), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11137 // __builtin_ve_vl_vsubswzx_vvvvl
11138 .{ .tag = @enumFromInt(2983), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11139 // __builtin_ve_vl_vsubul_vsvl
11140 .{ .tag = @enumFromInt(2984), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11141 // __builtin_ve_vl_vsubul_vsvmvl
11142 .{ .tag = @enumFromInt(2985), .properties = .{ .param_str = "V256dLUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11143 // __builtin_ve_vl_vsubul_vsvvl
11144 .{ .tag = @enumFromInt(2986), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11145 // __builtin_ve_vl_vsubul_vvvl
11146 .{ .tag = @enumFromInt(2987), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11147 // __builtin_ve_vl_vsubul_vvvmvl
11148 .{ .tag = @enumFromInt(2988), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11149 // __builtin_ve_vl_vsubul_vvvvl
11150 .{ .tag = @enumFromInt(2989), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11151 // __builtin_ve_vl_vsubuw_vsvl
11152 .{ .tag = @enumFromInt(2990), .properties = .{ .param_str = "V256dUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11153 // __builtin_ve_vl_vsubuw_vsvmvl
11154 .{ .tag = @enumFromInt(2991), .properties = .{ .param_str = "V256dUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11155 // __builtin_ve_vl_vsubuw_vsvvl
11156 .{ .tag = @enumFromInt(2992), .properties = .{ .param_str = "V256dUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11157 // __builtin_ve_vl_vsubuw_vvvl
11158 .{ .tag = @enumFromInt(2993), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11159 // __builtin_ve_vl_vsubuw_vvvmvl
11160 .{ .tag = @enumFromInt(2994), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11161 // __builtin_ve_vl_vsubuw_vvvvl
11162 .{ .tag = @enumFromInt(2995), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11163 // __builtin_ve_vl_vsuml_vvl
11164 .{ .tag = @enumFromInt(2996), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11165 // __builtin_ve_vl_vsuml_vvml
11166 .{ .tag = @enumFromInt(2997), .properties = .{ .param_str = "V256dV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11167 // __builtin_ve_vl_vsumwsx_vvl
11168 .{ .tag = @enumFromInt(2998), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11169 // __builtin_ve_vl_vsumwsx_vvml
11170 .{ .tag = @enumFromInt(2999), .properties = .{ .param_str = "V256dV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11171 // __builtin_ve_vl_vsumwzx_vvl
11172 .{ .tag = @enumFromInt(3000), .properties = .{ .param_str = "V256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11173 // __builtin_ve_vl_vsumwzx_vvml
11174 .{ .tag = @enumFromInt(3001), .properties = .{ .param_str = "V256dV256dV256bUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11175 // __builtin_ve_vl_vxor_vsvl
11176 .{ .tag = @enumFromInt(3002), .properties = .{ .param_str = "V256dLUiV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11177 // __builtin_ve_vl_vxor_vsvmvl
11178 .{ .tag = @enumFromInt(3003), .properties = .{ .param_str = "V256dLUiV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11179 // __builtin_ve_vl_vxor_vsvvl
11180 .{ .tag = @enumFromInt(3004), .properties = .{ .param_str = "V256dLUiV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11181 // __builtin_ve_vl_vxor_vvvl
11182 .{ .tag = @enumFromInt(3005), .properties = .{ .param_str = "V256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11183 // __builtin_ve_vl_vxor_vvvmvl
11184 .{ .tag = @enumFromInt(3006), .properties = .{ .param_str = "V256dV256dV256dV256bV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11185 // __builtin_ve_vl_vxor_vvvvl
11186 .{ .tag = @enumFromInt(3007), .properties = .{ .param_str = "V256dV256dV256dV256dUi", .target_set = TargetSet.initOne(.vevl_gen) } },
11187 // __builtin_ve_vl_xorm_MMM
11188 .{ .tag = @enumFromInt(3008), .properties = .{ .param_str = "V512bV512bV512b", .target_set = TargetSet.initOne(.vevl_gen) } },
11189 // __builtin_ve_vl_xorm_mmm
11190 .{ .tag = @enumFromInt(3009), .properties = .{ .param_str = "V256bV256bV256b", .target_set = TargetSet.initOne(.vevl_gen) } },
11191 // __builtin_vfprintf
11192 .{ .tag = @enumFromInt(3010), .properties = .{ .param_str = "iP*RcC*Ra", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .vprintf, .format_string_position = 1 } } },
11193 // __builtin_vfscanf
11194 .{ .tag = @enumFromInt(3011), .properties = .{ .param_str = "iP*RcC*Ra", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .vscanf, .format_string_position = 1 } } },
11195 // __builtin_vprintf
11196 .{ .tag = @enumFromInt(3012), .properties = .{ .param_str = "icC*Ra", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .vprintf } } },
11197 // __builtin_vscanf
11198 .{ .tag = @enumFromInt(3013), .properties = .{ .param_str = "icC*Ra", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .vscanf } } },
11199 // __builtin_vsnprintf
11200 .{ .tag = @enumFromInt(3014), .properties = .{ .param_str = "ic*RzcC*Ra", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .vprintf, .format_string_position = 2 } } },
11201 // __builtin_vsprintf
11202 .{ .tag = @enumFromInt(3015), .properties = .{ .param_str = "ic*RcC*Ra", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .vprintf, .format_string_position = 1 } } },
11203 // __builtin_vsscanf
11204 .{ .tag = @enumFromInt(3016), .properties = .{ .param_str = "icC*RcC*Ra", .attributes = .{ .lib_function_with_builtin_prefix = true, .format_kind = .vscanf, .format_string_position = 1 } } },
11205 // __builtin_wasm_max_f32
11206 .{ .tag = @enumFromInt(3017), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11207 // __builtin_wasm_max_f64
11208 .{ .tag = @enumFromInt(3018), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11209 // __builtin_wasm_memory_grow
11210 .{ .tag = @enumFromInt(3019), .properties = .{ .param_str = "zIiz", .target_set = TargetSet.initOne(.webassembly) } },
11211 // __builtin_wasm_memory_size
11212 .{ .tag = @enumFromInt(3020), .properties = .{ .param_str = "zIi", .target_set = TargetSet.initOne(.webassembly) } },
11213 // __builtin_wasm_min_f32
11214 .{ .tag = @enumFromInt(3021), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11215 // __builtin_wasm_min_f64
11216 .{ .tag = @enumFromInt(3022), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11217 // __builtin_wasm_trunc_s_i32_f32
11218 .{ .tag = @enumFromInt(3023), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11219 // __builtin_wasm_trunc_s_i32_f64
11220 .{ .tag = @enumFromInt(3024), .properties = .{ .param_str = "id", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11221 // __builtin_wasm_trunc_s_i64_f32
11222 .{ .tag = @enumFromInt(3025), .properties = .{ .param_str = "LLif", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11223 // __builtin_wasm_trunc_s_i64_f64
11224 .{ .tag = @enumFromInt(3026), .properties = .{ .param_str = "LLid", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11225 // __builtin_wasm_trunc_u_i32_f32
11226 .{ .tag = @enumFromInt(3027), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11227 // __builtin_wasm_trunc_u_i32_f64
11228 .{ .tag = @enumFromInt(3028), .properties = .{ .param_str = "id", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11229 // __builtin_wasm_trunc_u_i64_f32
11230 .{ .tag = @enumFromInt(3029), .properties = .{ .param_str = "LLif", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11231 // __builtin_wasm_trunc_u_i64_f64
11232 .{ .tag = @enumFromInt(3030), .properties = .{ .param_str = "LLid", .target_set = TargetSet.initOne(.webassembly), .attributes = .{ .@"const" = true } } },
11233 // __builtin_wcschr
11234 .{ .tag = @enumFromInt(3031), .properties = .{ .param_str = "w*wC*w", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
11235 // __builtin_wcscmp
11236 .{ .tag = @enumFromInt(3032), .properties = .{ .param_str = "iwC*wC*", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
11237 // __builtin_wcslen
11238 .{ .tag = @enumFromInt(3033), .properties = .{ .param_str = "zwC*", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
11239 // __builtin_wcsncmp
11240 .{ .tag = @enumFromInt(3034), .properties = .{ .param_str = "iwC*wC*z", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
11241 // __builtin_wmemchr
11242 .{ .tag = @enumFromInt(3035), .properties = .{ .param_str = "w*wC*wz", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
11243 // __builtin_wmemcmp
11244 .{ .tag = @enumFromInt(3036), .properties = .{ .param_str = "iwC*wC*z", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
11245 // __builtin_wmemcpy
11246 .{ .tag = @enumFromInt(3037), .properties = .{ .param_str = "w*w*wC*z", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
11247 // __builtin_wmemmove
11248 .{ .tag = @enumFromInt(3038), .properties = .{ .param_str = "w*w*wC*z", .attributes = .{ .lib_function_with_builtin_prefix = true, .const_evaluable = true } } },
11249 // __c11_atomic_compare_exchange_strong
11250 .{ .tag = @enumFromInt(3039), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11251 // __c11_atomic_compare_exchange_weak
11252 .{ .tag = @enumFromInt(3040), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11253 // __c11_atomic_exchange
11254 .{ .tag = @enumFromInt(3041), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11255 // __c11_atomic_fetch_add
11256 .{ .tag = @enumFromInt(3042), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11257 // __c11_atomic_fetch_and
11258 .{ .tag = @enumFromInt(3043), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11259 // __c11_atomic_fetch_max
11260 .{ .tag = @enumFromInt(3044), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11261 // __c11_atomic_fetch_min
11262 .{ .tag = @enumFromInt(3045), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11263 // __c11_atomic_fetch_nand
11264 .{ .tag = @enumFromInt(3046), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11265 // __c11_atomic_fetch_or
11266 .{ .tag = @enumFromInt(3047), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11267 // __c11_atomic_fetch_sub
11268 .{ .tag = @enumFromInt(3048), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11269 // __c11_atomic_fetch_xor
11270 .{ .tag = @enumFromInt(3049), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11271 // __c11_atomic_init
11272 .{ .tag = @enumFromInt(3050), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11273 // __c11_atomic_is_lock_free
11274 .{ .tag = @enumFromInt(3051), .properties = .{ .param_str = "bz", .attributes = .{ .const_evaluable = true } } },
11275 // __c11_atomic_load
11276 .{ .tag = @enumFromInt(3052), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11277 // __c11_atomic_signal_fence
11278 .{ .tag = @enumFromInt(3053), .properties = .{ .param_str = "vi" } },
11279 // __c11_atomic_store
11280 .{ .tag = @enumFromInt(3054), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
11281 // __c11_atomic_thread_fence
11282 .{ .tag = @enumFromInt(3055), .properties = .{ .param_str = "vi" } },
11283 // __clear_cache
11284 .{ .tag = @enumFromInt(3056), .properties = .{ .param_str = "vv*v*", .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
11285 // __cospi
11286 .{ .tag = @enumFromInt(3057), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
11287 // __cospif
11288 .{ .tag = @enumFromInt(3058), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
11289 // __debugbreak
11290 .{ .tag = @enumFromInt(3059), .properties = .{ .param_str = "v", .language = .all_ms_languages } },
11291 // __dmb
11292 .{ .tag = @enumFromInt(3060), .properties = .{ .param_str = "vUi", .language = .all_ms_languages, .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
11293 // __dsb
11294 .{ .tag = @enumFromInt(3061), .properties = .{ .param_str = "vUi", .language = .all_ms_languages, .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
11295 // __emit
11296 .{ .tag = @enumFromInt(3062), .properties = .{ .param_str = "vIUiC", .language = .all_ms_languages, .target_set = TargetSet.initOne(.arm) } },
11297 // __exception_code
11298 .{ .tag = @enumFromInt(3063), .properties = .{ .param_str = "UNi", .language = .all_ms_languages } },
11299 // __exception_info
11300 .{ .tag = @enumFromInt(3064), .properties = .{ .param_str = "v*", .language = .all_ms_languages } },
11301 // __exp10
11302 .{ .tag = @enumFromInt(3065), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
11303 // __exp10f
11304 .{ .tag = @enumFromInt(3066), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
11305 // __fastfail
11306 .{ .tag = @enumFromInt(3067), .properties = .{ .param_str = "vUi", .language = .all_ms_languages, .attributes = .{ .noreturn = true } } },
11307 // __finite
11308 .{ .tag = @enumFromInt(3068), .properties = .{ .param_str = "id", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
11309 // __finitef
11310 .{ .tag = @enumFromInt(3069), .properties = .{ .param_str = "if", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
11311 // __finitel
11312 .{ .tag = @enumFromInt(3070), .properties = .{ .param_str = "iLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
11313 // __isb
11314 .{ .tag = @enumFromInt(3071), .properties = .{ .param_str = "vUi", .language = .all_ms_languages, .target_set = TargetSet.initMany(&.{ .aarch64, .arm }), .attributes = .{ .@"const" = true } } },
11315 // __iso_volatile_load16
11316 .{ .tag = @enumFromInt(3072), .properties = .{ .param_str = "ssCD*", .language = .all_ms_languages } },
11317 // __iso_volatile_load32
11318 .{ .tag = @enumFromInt(3073), .properties = .{ .param_str = "iiCD*", .language = .all_ms_languages } },
11319 // __iso_volatile_load64
11320 .{ .tag = @enumFromInt(3074), .properties = .{ .param_str = "LLiLLiCD*", .language = .all_ms_languages } },
11321 // __iso_volatile_load8
11322 .{ .tag = @enumFromInt(3075), .properties = .{ .param_str = "ccCD*", .language = .all_ms_languages } },
11323 // __iso_volatile_store16
11324 .{ .tag = @enumFromInt(3076), .properties = .{ .param_str = "vsD*s", .language = .all_ms_languages } },
11325 // __iso_volatile_store32
11326 .{ .tag = @enumFromInt(3077), .properties = .{ .param_str = "viD*i", .language = .all_ms_languages } },
11327 // __iso_volatile_store64
11328 .{ .tag = @enumFromInt(3078), .properties = .{ .param_str = "vLLiD*LLi", .language = .all_ms_languages } },
11329 // __iso_volatile_store8
11330 .{ .tag = @enumFromInt(3079), .properties = .{ .param_str = "vcD*c", .language = .all_ms_languages } },
11331 // __ldrexd
11332 .{ .tag = @enumFromInt(3080), .properties = .{ .param_str = "WiWiCD*", .language = .all_ms_languages, .target_set = TargetSet.initOne(.arm) } },
11333 // __lzcnt
11334 .{ .tag = @enumFromInt(3081), .properties = .{ .param_str = "UiUi", .language = .all_ms_languages, .attributes = .{ .@"const" = true, .const_evaluable = true } } },
11335 // __lzcnt16
11336 .{ .tag = @enumFromInt(3082), .properties = .{ .param_str = "UsUs", .language = .all_ms_languages, .attributes = .{ .@"const" = true, .const_evaluable = true } } },
11337 // __lzcnt64
11338 .{ .tag = @enumFromInt(3083), .properties = .{ .param_str = "UWiUWi", .language = .all_ms_languages, .attributes = .{ .@"const" = true, .const_evaluable = true } } },
11339 // __noop
11340 .{ .tag = @enumFromInt(3084), .properties = .{ .param_str = "i.", .language = .all_ms_languages } },
11341 // __nvvm_add_rm_d
11342 .{ .tag = @enumFromInt(3085), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11343 // __nvvm_add_rm_f
11344 .{ .tag = @enumFromInt(3086), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11345 // __nvvm_add_rm_ftz_f
11346 .{ .tag = @enumFromInt(3087), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11347 // __nvvm_add_rn_d
11348 .{ .tag = @enumFromInt(3088), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11349 // __nvvm_add_rn_f
11350 .{ .tag = @enumFromInt(3089), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11351 // __nvvm_add_rn_ftz_f
11352 .{ .tag = @enumFromInt(3090), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11353 // __nvvm_add_rp_d
11354 .{ .tag = @enumFromInt(3091), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11355 // __nvvm_add_rp_f
11356 .{ .tag = @enumFromInt(3092), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11357 // __nvvm_add_rp_ftz_f
11358 .{ .tag = @enumFromInt(3093), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11359 // __nvvm_add_rz_d
11360 .{ .tag = @enumFromInt(3094), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11361 // __nvvm_add_rz_f
11362 .{ .tag = @enumFromInt(3095), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11363 // __nvvm_add_rz_ftz_f
11364 .{ .tag = @enumFromInt(3096), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11365 // __nvvm_atom_add_gen_f
11366 .{ .tag = @enumFromInt(3097), .properties = .{ .param_str = "ffD*f", .target_set = TargetSet.initOne(.nvptx) } },
11367 // __nvvm_atom_add_gen_i
11368 .{ .tag = @enumFromInt(3098), .properties = .{ .param_str = "iiD*i", .target_set = TargetSet.initOne(.nvptx) } },
11369 // __nvvm_atom_add_gen_l
11370 .{ .tag = @enumFromInt(3099), .properties = .{ .param_str = "LiLiD*Li", .target_set = TargetSet.initOne(.nvptx) } },
11371 // __nvvm_atom_add_gen_ll
11372 .{ .tag = @enumFromInt(3100), .properties = .{ .param_str = "LLiLLiD*LLi", .target_set = TargetSet.initOne(.nvptx) } },
11373 // __nvvm_atom_and_gen_i
11374 .{ .tag = @enumFromInt(3101), .properties = .{ .param_str = "iiD*i", .target_set = TargetSet.initOne(.nvptx) } },
11375 // __nvvm_atom_and_gen_l
11376 .{ .tag = @enumFromInt(3102), .properties = .{ .param_str = "LiLiD*Li", .target_set = TargetSet.initOne(.nvptx) } },
11377 // __nvvm_atom_and_gen_ll
11378 .{ .tag = @enumFromInt(3103), .properties = .{ .param_str = "LLiLLiD*LLi", .target_set = TargetSet.initOne(.nvptx) } },
11379 // __nvvm_atom_cas_gen_i
11380 .{ .tag = @enumFromInt(3104), .properties = .{ .param_str = "iiD*ii", .target_set = TargetSet.initOne(.nvptx) } },
11381 // __nvvm_atom_cas_gen_l
11382 .{ .tag = @enumFromInt(3105), .properties = .{ .param_str = "LiLiD*LiLi", .target_set = TargetSet.initOne(.nvptx) } },
11383 // __nvvm_atom_cas_gen_ll
11384 .{ .tag = @enumFromInt(3106), .properties = .{ .param_str = "LLiLLiD*LLiLLi", .target_set = TargetSet.initOne(.nvptx) } },
11385 // __nvvm_atom_dec_gen_ui
11386 .{ .tag = @enumFromInt(3107), .properties = .{ .param_str = "UiUiD*Ui", .target_set = TargetSet.initOne(.nvptx) } },
11387 // __nvvm_atom_inc_gen_ui
11388 .{ .tag = @enumFromInt(3108), .properties = .{ .param_str = "UiUiD*Ui", .target_set = TargetSet.initOne(.nvptx) } },
11389 // __nvvm_atom_max_gen_i
11390 .{ .tag = @enumFromInt(3109), .properties = .{ .param_str = "iiD*i", .target_set = TargetSet.initOne(.nvptx) } },
11391 // __nvvm_atom_max_gen_l
11392 .{ .tag = @enumFromInt(3110), .properties = .{ .param_str = "LiLiD*Li", .target_set = TargetSet.initOne(.nvptx) } },
11393 // __nvvm_atom_max_gen_ll
11394 .{ .tag = @enumFromInt(3111), .properties = .{ .param_str = "LLiLLiD*LLi", .target_set = TargetSet.initOne(.nvptx) } },
11395 // __nvvm_atom_max_gen_ui
11396 .{ .tag = @enumFromInt(3112), .properties = .{ .param_str = "UiUiD*Ui", .target_set = TargetSet.initOne(.nvptx) } },
11397 // __nvvm_atom_max_gen_ul
11398 .{ .tag = @enumFromInt(3113), .properties = .{ .param_str = "ULiULiD*ULi", .target_set = TargetSet.initOne(.nvptx) } },
11399 // __nvvm_atom_max_gen_ull
11400 .{ .tag = @enumFromInt(3114), .properties = .{ .param_str = "ULLiULLiD*ULLi", .target_set = TargetSet.initOne(.nvptx) } },
11401 // __nvvm_atom_min_gen_i
11402 .{ .tag = @enumFromInt(3115), .properties = .{ .param_str = "iiD*i", .target_set = TargetSet.initOne(.nvptx) } },
11403 // __nvvm_atom_min_gen_l
11404 .{ .tag = @enumFromInt(3116), .properties = .{ .param_str = "LiLiD*Li", .target_set = TargetSet.initOne(.nvptx) } },
11405 // __nvvm_atom_min_gen_ll
11406 .{ .tag = @enumFromInt(3117), .properties = .{ .param_str = "LLiLLiD*LLi", .target_set = TargetSet.initOne(.nvptx) } },
11407 // __nvvm_atom_min_gen_ui
11408 .{ .tag = @enumFromInt(3118), .properties = .{ .param_str = "UiUiD*Ui", .target_set = TargetSet.initOne(.nvptx) } },
11409 // __nvvm_atom_min_gen_ul
11410 .{ .tag = @enumFromInt(3119), .properties = .{ .param_str = "ULiULiD*ULi", .target_set = TargetSet.initOne(.nvptx) } },
11411 // __nvvm_atom_min_gen_ull
11412 .{ .tag = @enumFromInt(3120), .properties = .{ .param_str = "ULLiULLiD*ULLi", .target_set = TargetSet.initOne(.nvptx) } },
11413 // __nvvm_atom_or_gen_i
11414 .{ .tag = @enumFromInt(3121), .properties = .{ .param_str = "iiD*i", .target_set = TargetSet.initOne(.nvptx) } },
11415 // __nvvm_atom_or_gen_l
11416 .{ .tag = @enumFromInt(3122), .properties = .{ .param_str = "LiLiD*Li", .target_set = TargetSet.initOne(.nvptx) } },
11417 // __nvvm_atom_or_gen_ll
11418 .{ .tag = @enumFromInt(3123), .properties = .{ .param_str = "LLiLLiD*LLi", .target_set = TargetSet.initOne(.nvptx) } },
11419 // __nvvm_atom_sub_gen_i
11420 .{ .tag = @enumFromInt(3124), .properties = .{ .param_str = "iiD*i", .target_set = TargetSet.initOne(.nvptx) } },
11421 // __nvvm_atom_sub_gen_l
11422 .{ .tag = @enumFromInt(3125), .properties = .{ .param_str = "LiLiD*Li", .target_set = TargetSet.initOne(.nvptx) } },
11423 // __nvvm_atom_sub_gen_ll
11424 .{ .tag = @enumFromInt(3126), .properties = .{ .param_str = "LLiLLiD*LLi", .target_set = TargetSet.initOne(.nvptx) } },
11425 // __nvvm_atom_xchg_gen_i
11426 .{ .tag = @enumFromInt(3127), .properties = .{ .param_str = "iiD*i", .target_set = TargetSet.initOne(.nvptx) } },
11427 // __nvvm_atom_xchg_gen_l
11428 .{ .tag = @enumFromInt(3128), .properties = .{ .param_str = "LiLiD*Li", .target_set = TargetSet.initOne(.nvptx) } },
11429 // __nvvm_atom_xchg_gen_ll
11430 .{ .tag = @enumFromInt(3129), .properties = .{ .param_str = "LLiLLiD*LLi", .target_set = TargetSet.initOne(.nvptx) } },
11431 // __nvvm_atom_xor_gen_i
11432 .{ .tag = @enumFromInt(3130), .properties = .{ .param_str = "iiD*i", .target_set = TargetSet.initOne(.nvptx) } },
11433 // __nvvm_atom_xor_gen_l
11434 .{ .tag = @enumFromInt(3131), .properties = .{ .param_str = "LiLiD*Li", .target_set = TargetSet.initOne(.nvptx) } },
11435 // __nvvm_atom_xor_gen_ll
11436 .{ .tag = @enumFromInt(3132), .properties = .{ .param_str = "LLiLLiD*LLi", .target_set = TargetSet.initOne(.nvptx) } },
11437 // __nvvm_bar0_and
11438 .{ .tag = @enumFromInt(3133), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.nvptx) } },
11439 // __nvvm_bar0_or
11440 .{ .tag = @enumFromInt(3134), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.nvptx) } },
11441 // __nvvm_bar0_popc
11442 .{ .tag = @enumFromInt(3135), .properties = .{ .param_str = "ii", .target_set = TargetSet.initOne(.nvptx) } },
11443 // __nvvm_bar_sync
11444 .{ .tag = @enumFromInt(3136), .properties = .{ .param_str = "vi", .target_set = TargetSet.initOne(.nvptx) } },
11445 // __nvvm_bitcast_d2ll
11446 .{ .tag = @enumFromInt(3137), .properties = .{ .param_str = "LLid", .target_set = TargetSet.initOne(.nvptx) } },
11447 // __nvvm_bitcast_f2i
11448 .{ .tag = @enumFromInt(3138), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.nvptx) } },
11449 // __nvvm_bitcast_i2f
11450 .{ .tag = @enumFromInt(3139), .properties = .{ .param_str = "fi", .target_set = TargetSet.initOne(.nvptx) } },
11451 // __nvvm_bitcast_ll2d
11452 .{ .tag = @enumFromInt(3140), .properties = .{ .param_str = "dLLi", .target_set = TargetSet.initOne(.nvptx) } },
11453 // __nvvm_ceil_d
11454 .{ .tag = @enumFromInt(3141), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
11455 // __nvvm_ceil_f
11456 .{ .tag = @enumFromInt(3142), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11457 // __nvvm_ceil_ftz_f
11458 .{ .tag = @enumFromInt(3143), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11459 // __nvvm_compiler_error
11460 .{ .tag = @enumFromInt(3144), .properties = .{ .param_str = "vcC*4", .target_set = TargetSet.initOne(.nvptx) } },
11461 // __nvvm_compiler_warn
11462 .{ .tag = @enumFromInt(3145), .properties = .{ .param_str = "vcC*4", .target_set = TargetSet.initOne(.nvptx) } },
11463 // __nvvm_cos_approx_f
11464 .{ .tag = @enumFromInt(3146), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11465 // __nvvm_cos_approx_ftz_f
11466 .{ .tag = @enumFromInt(3147), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11467 // __nvvm_d2f_rm
11468 .{ .tag = @enumFromInt(3148), .properties = .{ .param_str = "fd", .target_set = TargetSet.initOne(.nvptx) } },
11469 // __nvvm_d2f_rm_ftz
11470 .{ .tag = @enumFromInt(3149), .properties = .{ .param_str = "fd", .target_set = TargetSet.initOne(.nvptx) } },
11471 // __nvvm_d2f_rn
11472 .{ .tag = @enumFromInt(3150), .properties = .{ .param_str = "fd", .target_set = TargetSet.initOne(.nvptx) } },
11473 // __nvvm_d2f_rn_ftz
11474 .{ .tag = @enumFromInt(3151), .properties = .{ .param_str = "fd", .target_set = TargetSet.initOne(.nvptx) } },
11475 // __nvvm_d2f_rp
11476 .{ .tag = @enumFromInt(3152), .properties = .{ .param_str = "fd", .target_set = TargetSet.initOne(.nvptx) } },
11477 // __nvvm_d2f_rp_ftz
11478 .{ .tag = @enumFromInt(3153), .properties = .{ .param_str = "fd", .target_set = TargetSet.initOne(.nvptx) } },
11479 // __nvvm_d2f_rz
11480 .{ .tag = @enumFromInt(3154), .properties = .{ .param_str = "fd", .target_set = TargetSet.initOne(.nvptx) } },
11481 // __nvvm_d2f_rz_ftz
11482 .{ .tag = @enumFromInt(3155), .properties = .{ .param_str = "fd", .target_set = TargetSet.initOne(.nvptx) } },
11483 // __nvvm_d2i_hi
11484 .{ .tag = @enumFromInt(3156), .properties = .{ .param_str = "id", .target_set = TargetSet.initOne(.nvptx) } },
11485 // __nvvm_d2i_lo
11486 .{ .tag = @enumFromInt(3157), .properties = .{ .param_str = "id", .target_set = TargetSet.initOne(.nvptx) } },
11487 // __nvvm_d2i_rm
11488 .{ .tag = @enumFromInt(3158), .properties = .{ .param_str = "id", .target_set = TargetSet.initOne(.nvptx) } },
11489 // __nvvm_d2i_rn
11490 .{ .tag = @enumFromInt(3159), .properties = .{ .param_str = "id", .target_set = TargetSet.initOne(.nvptx) } },
11491 // __nvvm_d2i_rp
11492 .{ .tag = @enumFromInt(3160), .properties = .{ .param_str = "id", .target_set = TargetSet.initOne(.nvptx) } },
11493 // __nvvm_d2i_rz
11494 .{ .tag = @enumFromInt(3161), .properties = .{ .param_str = "id", .target_set = TargetSet.initOne(.nvptx) } },
11495 // __nvvm_d2ll_rm
11496 .{ .tag = @enumFromInt(3162), .properties = .{ .param_str = "LLid", .target_set = TargetSet.initOne(.nvptx) } },
11497 // __nvvm_d2ll_rn
11498 .{ .tag = @enumFromInt(3163), .properties = .{ .param_str = "LLid", .target_set = TargetSet.initOne(.nvptx) } },
11499 // __nvvm_d2ll_rp
11500 .{ .tag = @enumFromInt(3164), .properties = .{ .param_str = "LLid", .target_set = TargetSet.initOne(.nvptx) } },
11501 // __nvvm_d2ll_rz
11502 .{ .tag = @enumFromInt(3165), .properties = .{ .param_str = "LLid", .target_set = TargetSet.initOne(.nvptx) } },
11503 // __nvvm_d2ui_rm
11504 .{ .tag = @enumFromInt(3166), .properties = .{ .param_str = "Uid", .target_set = TargetSet.initOne(.nvptx) } },
11505 // __nvvm_d2ui_rn
11506 .{ .tag = @enumFromInt(3167), .properties = .{ .param_str = "Uid", .target_set = TargetSet.initOne(.nvptx) } },
11507 // __nvvm_d2ui_rp
11508 .{ .tag = @enumFromInt(3168), .properties = .{ .param_str = "Uid", .target_set = TargetSet.initOne(.nvptx) } },
11509 // __nvvm_d2ui_rz
11510 .{ .tag = @enumFromInt(3169), .properties = .{ .param_str = "Uid", .target_set = TargetSet.initOne(.nvptx) } },
11511 // __nvvm_d2ull_rm
11512 .{ .tag = @enumFromInt(3170), .properties = .{ .param_str = "ULLid", .target_set = TargetSet.initOne(.nvptx) } },
11513 // __nvvm_d2ull_rn
11514 .{ .tag = @enumFromInt(3171), .properties = .{ .param_str = "ULLid", .target_set = TargetSet.initOne(.nvptx) } },
11515 // __nvvm_d2ull_rp
11516 .{ .tag = @enumFromInt(3172), .properties = .{ .param_str = "ULLid", .target_set = TargetSet.initOne(.nvptx) } },
11517 // __nvvm_d2ull_rz
11518 .{ .tag = @enumFromInt(3173), .properties = .{ .param_str = "ULLid", .target_set = TargetSet.initOne(.nvptx) } },
11519 // __nvvm_div_approx_f
11520 .{ .tag = @enumFromInt(3174), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11521 // __nvvm_div_approx_ftz_f
11522 .{ .tag = @enumFromInt(3175), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11523 // __nvvm_div_rm_d
11524 .{ .tag = @enumFromInt(3176), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11525 // __nvvm_div_rm_f
11526 .{ .tag = @enumFromInt(3177), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11527 // __nvvm_div_rm_ftz_f
11528 .{ .tag = @enumFromInt(3178), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11529 // __nvvm_div_rn_d
11530 .{ .tag = @enumFromInt(3179), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11531 // __nvvm_div_rn_f
11532 .{ .tag = @enumFromInt(3180), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11533 // __nvvm_div_rn_ftz_f
11534 .{ .tag = @enumFromInt(3181), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11535 // __nvvm_div_rp_d
11536 .{ .tag = @enumFromInt(3182), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11537 // __nvvm_div_rp_f
11538 .{ .tag = @enumFromInt(3183), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11539 // __nvvm_div_rp_ftz_f
11540 .{ .tag = @enumFromInt(3184), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11541 // __nvvm_div_rz_d
11542 .{ .tag = @enumFromInt(3185), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11543 // __nvvm_div_rz_f
11544 .{ .tag = @enumFromInt(3186), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11545 // __nvvm_div_rz_ftz_f
11546 .{ .tag = @enumFromInt(3187), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11547 // __nvvm_ex2_approx_d
11548 .{ .tag = @enumFromInt(3188), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
11549 // __nvvm_ex2_approx_f
11550 .{ .tag = @enumFromInt(3189), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11551 // __nvvm_ex2_approx_ftz_f
11552 .{ .tag = @enumFromInt(3190), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11553 // __nvvm_f2h_rn
11554 .{ .tag = @enumFromInt(3191), .properties = .{ .param_str = "Usf", .target_set = TargetSet.initOne(.nvptx) } },
11555 // __nvvm_f2h_rn_ftz
11556 .{ .tag = @enumFromInt(3192), .properties = .{ .param_str = "Usf", .target_set = TargetSet.initOne(.nvptx) } },
11557 // __nvvm_f2i_rm
11558 .{ .tag = @enumFromInt(3193), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.nvptx) } },
11559 // __nvvm_f2i_rm_ftz
11560 .{ .tag = @enumFromInt(3194), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.nvptx) } },
11561 // __nvvm_f2i_rn
11562 .{ .tag = @enumFromInt(3195), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.nvptx) } },
11563 // __nvvm_f2i_rn_ftz
11564 .{ .tag = @enumFromInt(3196), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.nvptx) } },
11565 // __nvvm_f2i_rp
11566 .{ .tag = @enumFromInt(3197), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.nvptx) } },
11567 // __nvvm_f2i_rp_ftz
11568 .{ .tag = @enumFromInt(3198), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.nvptx) } },
11569 // __nvvm_f2i_rz
11570 .{ .tag = @enumFromInt(3199), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.nvptx) } },
11571 // __nvvm_f2i_rz_ftz
11572 .{ .tag = @enumFromInt(3200), .properties = .{ .param_str = "if", .target_set = TargetSet.initOne(.nvptx) } },
11573 // __nvvm_f2ll_rm
11574 .{ .tag = @enumFromInt(3201), .properties = .{ .param_str = "LLif", .target_set = TargetSet.initOne(.nvptx) } },
11575 // __nvvm_f2ll_rm_ftz
11576 .{ .tag = @enumFromInt(3202), .properties = .{ .param_str = "LLif", .target_set = TargetSet.initOne(.nvptx) } },
11577 // __nvvm_f2ll_rn
11578 .{ .tag = @enumFromInt(3203), .properties = .{ .param_str = "LLif", .target_set = TargetSet.initOne(.nvptx) } },
11579 // __nvvm_f2ll_rn_ftz
11580 .{ .tag = @enumFromInt(3204), .properties = .{ .param_str = "LLif", .target_set = TargetSet.initOne(.nvptx) } },
11581 // __nvvm_f2ll_rp
11582 .{ .tag = @enumFromInt(3205), .properties = .{ .param_str = "LLif", .target_set = TargetSet.initOne(.nvptx) } },
11583 // __nvvm_f2ll_rp_ftz
11584 .{ .tag = @enumFromInt(3206), .properties = .{ .param_str = "LLif", .target_set = TargetSet.initOne(.nvptx) } },
11585 // __nvvm_f2ll_rz
11586 .{ .tag = @enumFromInt(3207), .properties = .{ .param_str = "LLif", .target_set = TargetSet.initOne(.nvptx) } },
11587 // __nvvm_f2ll_rz_ftz
11588 .{ .tag = @enumFromInt(3208), .properties = .{ .param_str = "LLif", .target_set = TargetSet.initOne(.nvptx) } },
11589 // __nvvm_f2ui_rm
11590 .{ .tag = @enumFromInt(3209), .properties = .{ .param_str = "Uif", .target_set = TargetSet.initOne(.nvptx) } },
11591 // __nvvm_f2ui_rm_ftz
11592 .{ .tag = @enumFromInt(3210), .properties = .{ .param_str = "Uif", .target_set = TargetSet.initOne(.nvptx) } },
11593 // __nvvm_f2ui_rn
11594 .{ .tag = @enumFromInt(3211), .properties = .{ .param_str = "Uif", .target_set = TargetSet.initOne(.nvptx) } },
11595 // __nvvm_f2ui_rn_ftz
11596 .{ .tag = @enumFromInt(3212), .properties = .{ .param_str = "Uif", .target_set = TargetSet.initOne(.nvptx) } },
11597 // __nvvm_f2ui_rp
11598 .{ .tag = @enumFromInt(3213), .properties = .{ .param_str = "Uif", .target_set = TargetSet.initOne(.nvptx) } },
11599 // __nvvm_f2ui_rp_ftz
11600 .{ .tag = @enumFromInt(3214), .properties = .{ .param_str = "Uif", .target_set = TargetSet.initOne(.nvptx) } },
11601 // __nvvm_f2ui_rz
11602 .{ .tag = @enumFromInt(3215), .properties = .{ .param_str = "Uif", .target_set = TargetSet.initOne(.nvptx) } },
11603 // __nvvm_f2ui_rz_ftz
11604 .{ .tag = @enumFromInt(3216), .properties = .{ .param_str = "Uif", .target_set = TargetSet.initOne(.nvptx) } },
11605 // __nvvm_f2ull_rm
11606 .{ .tag = @enumFromInt(3217), .properties = .{ .param_str = "ULLif", .target_set = TargetSet.initOne(.nvptx) } },
11607 // __nvvm_f2ull_rm_ftz
11608 .{ .tag = @enumFromInt(3218), .properties = .{ .param_str = "ULLif", .target_set = TargetSet.initOne(.nvptx) } },
11609 // __nvvm_f2ull_rn
11610 .{ .tag = @enumFromInt(3219), .properties = .{ .param_str = "ULLif", .target_set = TargetSet.initOne(.nvptx) } },
11611 // __nvvm_f2ull_rn_ftz
11612 .{ .tag = @enumFromInt(3220), .properties = .{ .param_str = "ULLif", .target_set = TargetSet.initOne(.nvptx) } },
11613 // __nvvm_f2ull_rp
11614 .{ .tag = @enumFromInt(3221), .properties = .{ .param_str = "ULLif", .target_set = TargetSet.initOne(.nvptx) } },
11615 // __nvvm_f2ull_rp_ftz
11616 .{ .tag = @enumFromInt(3222), .properties = .{ .param_str = "ULLif", .target_set = TargetSet.initOne(.nvptx) } },
11617 // __nvvm_f2ull_rz
11618 .{ .tag = @enumFromInt(3223), .properties = .{ .param_str = "ULLif", .target_set = TargetSet.initOne(.nvptx) } },
11619 // __nvvm_f2ull_rz_ftz
11620 .{ .tag = @enumFromInt(3224), .properties = .{ .param_str = "ULLif", .target_set = TargetSet.initOne(.nvptx) } },
11621 // __nvvm_fabs_d
11622 .{ .tag = @enumFromInt(3225), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
11623 // __nvvm_fabs_f
11624 .{ .tag = @enumFromInt(3226), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11625 // __nvvm_fabs_ftz_f
11626 .{ .tag = @enumFromInt(3227), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11627 // __nvvm_floor_d
11628 .{ .tag = @enumFromInt(3228), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
11629 // __nvvm_floor_f
11630 .{ .tag = @enumFromInt(3229), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11631 // __nvvm_floor_ftz_f
11632 .{ .tag = @enumFromInt(3230), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11633 // __nvvm_fma_rm_d
11634 .{ .tag = @enumFromInt(3231), .properties = .{ .param_str = "dddd", .target_set = TargetSet.initOne(.nvptx) } },
11635 // __nvvm_fma_rm_f
11636 .{ .tag = @enumFromInt(3232), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.nvptx) } },
11637 // __nvvm_fma_rm_ftz_f
11638 .{ .tag = @enumFromInt(3233), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.nvptx) } },
11639 // __nvvm_fma_rn_d
11640 .{ .tag = @enumFromInt(3234), .properties = .{ .param_str = "dddd", .target_set = TargetSet.initOne(.nvptx) } },
11641 // __nvvm_fma_rn_f
11642 .{ .tag = @enumFromInt(3235), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.nvptx) } },
11643 // __nvvm_fma_rn_ftz_f
11644 .{ .tag = @enumFromInt(3236), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.nvptx) } },
11645 // __nvvm_fma_rp_d
11646 .{ .tag = @enumFromInt(3237), .properties = .{ .param_str = "dddd", .target_set = TargetSet.initOne(.nvptx) } },
11647 // __nvvm_fma_rp_f
11648 .{ .tag = @enumFromInt(3238), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.nvptx) } },
11649 // __nvvm_fma_rp_ftz_f
11650 .{ .tag = @enumFromInt(3239), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.nvptx) } },
11651 // __nvvm_fma_rz_d
11652 .{ .tag = @enumFromInt(3240), .properties = .{ .param_str = "dddd", .target_set = TargetSet.initOne(.nvptx) } },
11653 // __nvvm_fma_rz_f
11654 .{ .tag = @enumFromInt(3241), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.nvptx) } },
11655 // __nvvm_fma_rz_ftz_f
11656 .{ .tag = @enumFromInt(3242), .properties = .{ .param_str = "ffff", .target_set = TargetSet.initOne(.nvptx) } },
11657 // __nvvm_fmax_d
11658 .{ .tag = @enumFromInt(3243), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11659 // __nvvm_fmax_f
11660 .{ .tag = @enumFromInt(3244), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11661 // __nvvm_fmax_ftz_f
11662 .{ .tag = @enumFromInt(3245), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11663 // __nvvm_fmin_d
11664 .{ .tag = @enumFromInt(3246), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11665 // __nvvm_fmin_f
11666 .{ .tag = @enumFromInt(3247), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11667 // __nvvm_fmin_ftz_f
11668 .{ .tag = @enumFromInt(3248), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11669 // __nvvm_i2d_rm
11670 .{ .tag = @enumFromInt(3249), .properties = .{ .param_str = "di", .target_set = TargetSet.initOne(.nvptx) } },
11671 // __nvvm_i2d_rn
11672 .{ .tag = @enumFromInt(3250), .properties = .{ .param_str = "di", .target_set = TargetSet.initOne(.nvptx) } },
11673 // __nvvm_i2d_rp
11674 .{ .tag = @enumFromInt(3251), .properties = .{ .param_str = "di", .target_set = TargetSet.initOne(.nvptx) } },
11675 // __nvvm_i2d_rz
11676 .{ .tag = @enumFromInt(3252), .properties = .{ .param_str = "di", .target_set = TargetSet.initOne(.nvptx) } },
11677 // __nvvm_i2f_rm
11678 .{ .tag = @enumFromInt(3253), .properties = .{ .param_str = "fi", .target_set = TargetSet.initOne(.nvptx) } },
11679 // __nvvm_i2f_rn
11680 .{ .tag = @enumFromInt(3254), .properties = .{ .param_str = "fi", .target_set = TargetSet.initOne(.nvptx) } },
11681 // __nvvm_i2f_rp
11682 .{ .tag = @enumFromInt(3255), .properties = .{ .param_str = "fi", .target_set = TargetSet.initOne(.nvptx) } },
11683 // __nvvm_i2f_rz
11684 .{ .tag = @enumFromInt(3256), .properties = .{ .param_str = "fi", .target_set = TargetSet.initOne(.nvptx) } },
11685 // __nvvm_isspacep_const
11686 .{ .tag = @enumFromInt(3257), .properties = .{ .param_str = "bvC*", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11687 // __nvvm_isspacep_global
11688 .{ .tag = @enumFromInt(3258), .properties = .{ .param_str = "bvC*", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11689 // __nvvm_isspacep_local
11690 .{ .tag = @enumFromInt(3259), .properties = .{ .param_str = "bvC*", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11691 // __nvvm_isspacep_shared
11692 .{ .tag = @enumFromInt(3260), .properties = .{ .param_str = "bvC*", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11693 // __nvvm_ldg_c
11694 .{ .tag = @enumFromInt(3261), .properties = .{ .param_str = "ccC*", .target_set = TargetSet.initOne(.nvptx) } },
11695 // __nvvm_ldg_c2
11696 .{ .tag = @enumFromInt(3262), .properties = .{ .param_str = "E2cE2cC*", .target_set = TargetSet.initOne(.nvptx) } },
11697 // __nvvm_ldg_c4
11698 .{ .tag = @enumFromInt(3263), .properties = .{ .param_str = "E4cE4cC*", .target_set = TargetSet.initOne(.nvptx) } },
11699 // __nvvm_ldg_d
11700 .{ .tag = @enumFromInt(3264), .properties = .{ .param_str = "ddC*", .target_set = TargetSet.initOne(.nvptx) } },
11701 // __nvvm_ldg_d2
11702 .{ .tag = @enumFromInt(3265), .properties = .{ .param_str = "E2dE2dC*", .target_set = TargetSet.initOne(.nvptx) } },
11703 // __nvvm_ldg_f
11704 .{ .tag = @enumFromInt(3266), .properties = .{ .param_str = "ffC*", .target_set = TargetSet.initOne(.nvptx) } },
11705 // __nvvm_ldg_f2
11706 .{ .tag = @enumFromInt(3267), .properties = .{ .param_str = "E2fE2fC*", .target_set = TargetSet.initOne(.nvptx) } },
11707 // __nvvm_ldg_f4
11708 .{ .tag = @enumFromInt(3268), .properties = .{ .param_str = "E4fE4fC*", .target_set = TargetSet.initOne(.nvptx) } },
11709 // __nvvm_ldg_h
11710 .{ .tag = @enumFromInt(3269), .properties = .{ .param_str = "hhC*", .target_set = TargetSet.initOne(.nvptx) } },
11711 // __nvvm_ldg_h2
11712 .{ .tag = @enumFromInt(3270), .properties = .{ .param_str = "E2hE2hC*", .target_set = TargetSet.initOne(.nvptx) } },
11713 // __nvvm_ldg_i
11714 .{ .tag = @enumFromInt(3271), .properties = .{ .param_str = "iiC*", .target_set = TargetSet.initOne(.nvptx) } },
11715 // __nvvm_ldg_i2
11716 .{ .tag = @enumFromInt(3272), .properties = .{ .param_str = "E2iE2iC*", .target_set = TargetSet.initOne(.nvptx) } },
11717 // __nvvm_ldg_i4
11718 .{ .tag = @enumFromInt(3273), .properties = .{ .param_str = "E4iE4iC*", .target_set = TargetSet.initOne(.nvptx) } },
11719 // __nvvm_ldg_l
11720 .{ .tag = @enumFromInt(3274), .properties = .{ .param_str = "LiLiC*", .target_set = TargetSet.initOne(.nvptx) } },
11721 // __nvvm_ldg_l2
11722 .{ .tag = @enumFromInt(3275), .properties = .{ .param_str = "E2LiE2LiC*", .target_set = TargetSet.initOne(.nvptx) } },
11723 // __nvvm_ldg_ll
11724 .{ .tag = @enumFromInt(3276), .properties = .{ .param_str = "LLiLLiC*", .target_set = TargetSet.initOne(.nvptx) } },
11725 // __nvvm_ldg_ll2
11726 .{ .tag = @enumFromInt(3277), .properties = .{ .param_str = "E2LLiE2LLiC*", .target_set = TargetSet.initOne(.nvptx) } },
11727 // __nvvm_ldg_s
11728 .{ .tag = @enumFromInt(3278), .properties = .{ .param_str = "ssC*", .target_set = TargetSet.initOne(.nvptx) } },
11729 // __nvvm_ldg_s2
11730 .{ .tag = @enumFromInt(3279), .properties = .{ .param_str = "E2sE2sC*", .target_set = TargetSet.initOne(.nvptx) } },
11731 // __nvvm_ldg_s4
11732 .{ .tag = @enumFromInt(3280), .properties = .{ .param_str = "E4sE4sC*", .target_set = TargetSet.initOne(.nvptx) } },
11733 // __nvvm_ldg_sc
11734 .{ .tag = @enumFromInt(3281), .properties = .{ .param_str = "ScScC*", .target_set = TargetSet.initOne(.nvptx) } },
11735 // __nvvm_ldg_sc2
11736 .{ .tag = @enumFromInt(3282), .properties = .{ .param_str = "E2ScE2ScC*", .target_set = TargetSet.initOne(.nvptx) } },
11737 // __nvvm_ldg_sc4
11738 .{ .tag = @enumFromInt(3283), .properties = .{ .param_str = "E4ScE4ScC*", .target_set = TargetSet.initOne(.nvptx) } },
11739 // __nvvm_ldg_uc
11740 .{ .tag = @enumFromInt(3284), .properties = .{ .param_str = "UcUcC*", .target_set = TargetSet.initOne(.nvptx) } },
11741 // __nvvm_ldg_uc2
11742 .{ .tag = @enumFromInt(3285), .properties = .{ .param_str = "E2UcE2UcC*", .target_set = TargetSet.initOne(.nvptx) } },
11743 // __nvvm_ldg_uc4
11744 .{ .tag = @enumFromInt(3286), .properties = .{ .param_str = "E4UcE4UcC*", .target_set = TargetSet.initOne(.nvptx) } },
11745 // __nvvm_ldg_ui
11746 .{ .tag = @enumFromInt(3287), .properties = .{ .param_str = "UiUiC*", .target_set = TargetSet.initOne(.nvptx) } },
11747 // __nvvm_ldg_ui2
11748 .{ .tag = @enumFromInt(3288), .properties = .{ .param_str = "E2UiE2UiC*", .target_set = TargetSet.initOne(.nvptx) } },
11749 // __nvvm_ldg_ui4
11750 .{ .tag = @enumFromInt(3289), .properties = .{ .param_str = "E4UiE4UiC*", .target_set = TargetSet.initOne(.nvptx) } },
11751 // __nvvm_ldg_ul
11752 .{ .tag = @enumFromInt(3290), .properties = .{ .param_str = "ULiULiC*", .target_set = TargetSet.initOne(.nvptx) } },
11753 // __nvvm_ldg_ul2
11754 .{ .tag = @enumFromInt(3291), .properties = .{ .param_str = "E2ULiE2ULiC*", .target_set = TargetSet.initOne(.nvptx) } },
11755 // __nvvm_ldg_ull
11756 .{ .tag = @enumFromInt(3292), .properties = .{ .param_str = "ULLiULLiC*", .target_set = TargetSet.initOne(.nvptx) } },
11757 // __nvvm_ldg_ull2
11758 .{ .tag = @enumFromInt(3293), .properties = .{ .param_str = "E2ULLiE2ULLiC*", .target_set = TargetSet.initOne(.nvptx) } },
11759 // __nvvm_ldg_us
11760 .{ .tag = @enumFromInt(3294), .properties = .{ .param_str = "UsUsC*", .target_set = TargetSet.initOne(.nvptx) } },
11761 // __nvvm_ldg_us2
11762 .{ .tag = @enumFromInt(3295), .properties = .{ .param_str = "E2UsE2UsC*", .target_set = TargetSet.initOne(.nvptx) } },
11763 // __nvvm_ldg_us4
11764 .{ .tag = @enumFromInt(3296), .properties = .{ .param_str = "E4UsE4UsC*", .target_set = TargetSet.initOne(.nvptx) } },
11765 // __nvvm_ldu_c
11766 .{ .tag = @enumFromInt(3297), .properties = .{ .param_str = "ccC*", .target_set = TargetSet.initOne(.nvptx) } },
11767 // __nvvm_ldu_c2
11768 .{ .tag = @enumFromInt(3298), .properties = .{ .param_str = "E2cE2cC*", .target_set = TargetSet.initOne(.nvptx) } },
11769 // __nvvm_ldu_c4
11770 .{ .tag = @enumFromInt(3299), .properties = .{ .param_str = "E4cE4cC*", .target_set = TargetSet.initOne(.nvptx) } },
11771 // __nvvm_ldu_d
11772 .{ .tag = @enumFromInt(3300), .properties = .{ .param_str = "ddC*", .target_set = TargetSet.initOne(.nvptx) } },
11773 // __nvvm_ldu_d2
11774 .{ .tag = @enumFromInt(3301), .properties = .{ .param_str = "E2dE2dC*", .target_set = TargetSet.initOne(.nvptx) } },
11775 // __nvvm_ldu_f
11776 .{ .tag = @enumFromInt(3302), .properties = .{ .param_str = "ffC*", .target_set = TargetSet.initOne(.nvptx) } },
11777 // __nvvm_ldu_f2
11778 .{ .tag = @enumFromInt(3303), .properties = .{ .param_str = "E2fE2fC*", .target_set = TargetSet.initOne(.nvptx) } },
11779 // __nvvm_ldu_f4
11780 .{ .tag = @enumFromInt(3304), .properties = .{ .param_str = "E4fE4fC*", .target_set = TargetSet.initOne(.nvptx) } },
11781 // __nvvm_ldu_h
11782 .{ .tag = @enumFromInt(3305), .properties = .{ .param_str = "hhC*", .target_set = TargetSet.initOne(.nvptx) } },
11783 // __nvvm_ldu_h2
11784 .{ .tag = @enumFromInt(3306), .properties = .{ .param_str = "E2hE2hC*", .target_set = TargetSet.initOne(.nvptx) } },
11785 // __nvvm_ldu_i
11786 .{ .tag = @enumFromInt(3307), .properties = .{ .param_str = "iiC*", .target_set = TargetSet.initOne(.nvptx) } },
11787 // __nvvm_ldu_i2
11788 .{ .tag = @enumFromInt(3308), .properties = .{ .param_str = "E2iE2iC*", .target_set = TargetSet.initOne(.nvptx) } },
11789 // __nvvm_ldu_i4
11790 .{ .tag = @enumFromInt(3309), .properties = .{ .param_str = "E4iE4iC*", .target_set = TargetSet.initOne(.nvptx) } },
11791 // __nvvm_ldu_l
11792 .{ .tag = @enumFromInt(3310), .properties = .{ .param_str = "LiLiC*", .target_set = TargetSet.initOne(.nvptx) } },
11793 // __nvvm_ldu_l2
11794 .{ .tag = @enumFromInt(3311), .properties = .{ .param_str = "E2LiE2LiC*", .target_set = TargetSet.initOne(.nvptx) } },
11795 // __nvvm_ldu_ll
11796 .{ .tag = @enumFromInt(3312), .properties = .{ .param_str = "LLiLLiC*", .target_set = TargetSet.initOne(.nvptx) } },
11797 // __nvvm_ldu_ll2
11798 .{ .tag = @enumFromInt(3313), .properties = .{ .param_str = "E2LLiE2LLiC*", .target_set = TargetSet.initOne(.nvptx) } },
11799 // __nvvm_ldu_s
11800 .{ .tag = @enumFromInt(3314), .properties = .{ .param_str = "ssC*", .target_set = TargetSet.initOne(.nvptx) } },
11801 // __nvvm_ldu_s2
11802 .{ .tag = @enumFromInt(3315), .properties = .{ .param_str = "E2sE2sC*", .target_set = TargetSet.initOne(.nvptx) } },
11803 // __nvvm_ldu_s4
11804 .{ .tag = @enumFromInt(3316), .properties = .{ .param_str = "E4sE4sC*", .target_set = TargetSet.initOne(.nvptx) } },
11805 // __nvvm_ldu_sc
11806 .{ .tag = @enumFromInt(3317), .properties = .{ .param_str = "ScScC*", .target_set = TargetSet.initOne(.nvptx) } },
11807 // __nvvm_ldu_sc2
11808 .{ .tag = @enumFromInt(3318), .properties = .{ .param_str = "E2ScE2ScC*", .target_set = TargetSet.initOne(.nvptx) } },
11809 // __nvvm_ldu_sc4
11810 .{ .tag = @enumFromInt(3319), .properties = .{ .param_str = "E4ScE4ScC*", .target_set = TargetSet.initOne(.nvptx) } },
11811 // __nvvm_ldu_uc
11812 .{ .tag = @enumFromInt(3320), .properties = .{ .param_str = "UcUcC*", .target_set = TargetSet.initOne(.nvptx) } },
11813 // __nvvm_ldu_uc2
11814 .{ .tag = @enumFromInt(3321), .properties = .{ .param_str = "E2UcE2UcC*", .target_set = TargetSet.initOne(.nvptx) } },
11815 // __nvvm_ldu_uc4
11816 .{ .tag = @enumFromInt(3322), .properties = .{ .param_str = "E4UcE4UcC*", .target_set = TargetSet.initOne(.nvptx) } },
11817 // __nvvm_ldu_ui
11818 .{ .tag = @enumFromInt(3323), .properties = .{ .param_str = "UiUiC*", .target_set = TargetSet.initOne(.nvptx) } },
11819 // __nvvm_ldu_ui2
11820 .{ .tag = @enumFromInt(3324), .properties = .{ .param_str = "E2UiE2UiC*", .target_set = TargetSet.initOne(.nvptx) } },
11821 // __nvvm_ldu_ui4
11822 .{ .tag = @enumFromInt(3325), .properties = .{ .param_str = "E4UiE4UiC*", .target_set = TargetSet.initOne(.nvptx) } },
11823 // __nvvm_ldu_ul
11824 .{ .tag = @enumFromInt(3326), .properties = .{ .param_str = "ULiULiC*", .target_set = TargetSet.initOne(.nvptx) } },
11825 // __nvvm_ldu_ul2
11826 .{ .tag = @enumFromInt(3327), .properties = .{ .param_str = "E2ULiE2ULiC*", .target_set = TargetSet.initOne(.nvptx) } },
11827 // __nvvm_ldu_ull
11828 .{ .tag = @enumFromInt(3328), .properties = .{ .param_str = "ULLiULLiC*", .target_set = TargetSet.initOne(.nvptx) } },
11829 // __nvvm_ldu_ull2
11830 .{ .tag = @enumFromInt(3329), .properties = .{ .param_str = "E2ULLiE2ULLiC*", .target_set = TargetSet.initOne(.nvptx) } },
11831 // __nvvm_ldu_us
11832 .{ .tag = @enumFromInt(3330), .properties = .{ .param_str = "UsUsC*", .target_set = TargetSet.initOne(.nvptx) } },
11833 // __nvvm_ldu_us2
11834 .{ .tag = @enumFromInt(3331), .properties = .{ .param_str = "E2UsE2UsC*", .target_set = TargetSet.initOne(.nvptx) } },
11835 // __nvvm_ldu_us4
11836 .{ .tag = @enumFromInt(3332), .properties = .{ .param_str = "E4UsE4UsC*", .target_set = TargetSet.initOne(.nvptx) } },
11837 // __nvvm_lg2_approx_d
11838 .{ .tag = @enumFromInt(3333), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
11839 // __nvvm_lg2_approx_f
11840 .{ .tag = @enumFromInt(3334), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11841 // __nvvm_lg2_approx_ftz_f
11842 .{ .tag = @enumFromInt(3335), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11843 // __nvvm_ll2d_rm
11844 .{ .tag = @enumFromInt(3336), .properties = .{ .param_str = "dLLi", .target_set = TargetSet.initOne(.nvptx) } },
11845 // __nvvm_ll2d_rn
11846 .{ .tag = @enumFromInt(3337), .properties = .{ .param_str = "dLLi", .target_set = TargetSet.initOne(.nvptx) } },
11847 // __nvvm_ll2d_rp
11848 .{ .tag = @enumFromInt(3338), .properties = .{ .param_str = "dLLi", .target_set = TargetSet.initOne(.nvptx) } },
11849 // __nvvm_ll2d_rz
11850 .{ .tag = @enumFromInt(3339), .properties = .{ .param_str = "dLLi", .target_set = TargetSet.initOne(.nvptx) } },
11851 // __nvvm_ll2f_rm
11852 .{ .tag = @enumFromInt(3340), .properties = .{ .param_str = "fLLi", .target_set = TargetSet.initOne(.nvptx) } },
11853 // __nvvm_ll2f_rn
11854 .{ .tag = @enumFromInt(3341), .properties = .{ .param_str = "fLLi", .target_set = TargetSet.initOne(.nvptx) } },
11855 // __nvvm_ll2f_rp
11856 .{ .tag = @enumFromInt(3342), .properties = .{ .param_str = "fLLi", .target_set = TargetSet.initOne(.nvptx) } },
11857 // __nvvm_ll2f_rz
11858 .{ .tag = @enumFromInt(3343), .properties = .{ .param_str = "fLLi", .target_set = TargetSet.initOne(.nvptx) } },
11859 // __nvvm_lohi_i2d
11860 .{ .tag = @enumFromInt(3344), .properties = .{ .param_str = "dii", .target_set = TargetSet.initOne(.nvptx) } },
11861 // __nvvm_membar_cta
11862 .{ .tag = @enumFromInt(3345), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.nvptx) } },
11863 // __nvvm_membar_gl
11864 .{ .tag = @enumFromInt(3346), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.nvptx) } },
11865 // __nvvm_membar_sys
11866 .{ .tag = @enumFromInt(3347), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.nvptx) } },
11867 // __nvvm_memcpy
11868 .{ .tag = @enumFromInt(3348), .properties = .{ .param_str = "vUc*Uc*zi", .target_set = TargetSet.initOne(.nvptx) } },
11869 // __nvvm_memset
11870 .{ .tag = @enumFromInt(3349), .properties = .{ .param_str = "vUc*Uczi", .target_set = TargetSet.initOne(.nvptx) } },
11871 // __nvvm_mul24_i
11872 .{ .tag = @enumFromInt(3350), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.nvptx) } },
11873 // __nvvm_mul24_ui
11874 .{ .tag = @enumFromInt(3351), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.nvptx) } },
11875 // __nvvm_mul_rm_d
11876 .{ .tag = @enumFromInt(3352), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11877 // __nvvm_mul_rm_f
11878 .{ .tag = @enumFromInt(3353), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11879 // __nvvm_mul_rm_ftz_f
11880 .{ .tag = @enumFromInt(3354), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11881 // __nvvm_mul_rn_d
11882 .{ .tag = @enumFromInt(3355), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11883 // __nvvm_mul_rn_f
11884 .{ .tag = @enumFromInt(3356), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11885 // __nvvm_mul_rn_ftz_f
11886 .{ .tag = @enumFromInt(3357), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11887 // __nvvm_mul_rp_d
11888 .{ .tag = @enumFromInt(3358), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11889 // __nvvm_mul_rp_f
11890 .{ .tag = @enumFromInt(3359), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11891 // __nvvm_mul_rp_ftz_f
11892 .{ .tag = @enumFromInt(3360), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11893 // __nvvm_mul_rz_d
11894 .{ .tag = @enumFromInt(3361), .properties = .{ .param_str = "ddd", .target_set = TargetSet.initOne(.nvptx) } },
11895 // __nvvm_mul_rz_f
11896 .{ .tag = @enumFromInt(3362), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11897 // __nvvm_mul_rz_ftz_f
11898 .{ .tag = @enumFromInt(3363), .properties = .{ .param_str = "fff", .target_set = TargetSet.initOne(.nvptx) } },
11899 // __nvvm_mulhi_i
11900 .{ .tag = @enumFromInt(3364), .properties = .{ .param_str = "iii", .target_set = TargetSet.initOne(.nvptx) } },
11901 // __nvvm_mulhi_ll
11902 .{ .tag = @enumFromInt(3365), .properties = .{ .param_str = "LLiLLiLLi", .target_set = TargetSet.initOne(.nvptx) } },
11903 // __nvvm_mulhi_ui
11904 .{ .tag = @enumFromInt(3366), .properties = .{ .param_str = "UiUiUi", .target_set = TargetSet.initOne(.nvptx) } },
11905 // __nvvm_mulhi_ull
11906 .{ .tag = @enumFromInt(3367), .properties = .{ .param_str = "ULLiULLiULLi", .target_set = TargetSet.initOne(.nvptx) } },
11907 // __nvvm_prmt
11908 .{ .tag = @enumFromInt(3368), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.nvptx) } },
11909 // __nvvm_rcp_approx_ftz_d
11910 .{ .tag = @enumFromInt(3369), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
11911 // __nvvm_rcp_approx_ftz_f
11912 .{ .tag = @enumFromInt(3370), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11913 // __nvvm_rcp_rm_d
11914 .{ .tag = @enumFromInt(3371), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
11915 // __nvvm_rcp_rm_f
11916 .{ .tag = @enumFromInt(3372), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11917 // __nvvm_rcp_rm_ftz_f
11918 .{ .tag = @enumFromInt(3373), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11919 // __nvvm_rcp_rn_d
11920 .{ .tag = @enumFromInt(3374), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
11921 // __nvvm_rcp_rn_f
11922 .{ .tag = @enumFromInt(3375), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11923 // __nvvm_rcp_rn_ftz_f
11924 .{ .tag = @enumFromInt(3376), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11925 // __nvvm_rcp_rp_d
11926 .{ .tag = @enumFromInt(3377), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
11927 // __nvvm_rcp_rp_f
11928 .{ .tag = @enumFromInt(3378), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11929 // __nvvm_rcp_rp_ftz_f
11930 .{ .tag = @enumFromInt(3379), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11931 // __nvvm_rcp_rz_d
11932 .{ .tag = @enumFromInt(3380), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
11933 // __nvvm_rcp_rz_f
11934 .{ .tag = @enumFromInt(3381), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11935 // __nvvm_rcp_rz_ftz_f
11936 .{ .tag = @enumFromInt(3382), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
11937 // __nvvm_read_ptx_sreg_clock
11938 .{ .tag = @enumFromInt(3383), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx) } },
11939 // __nvvm_read_ptx_sreg_clock64
11940 .{ .tag = @enumFromInt(3384), .properties = .{ .param_str = "LLi", .target_set = TargetSet.initOne(.nvptx) } },
11941 // __nvvm_read_ptx_sreg_ctaid_w
11942 .{ .tag = @enumFromInt(3385), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11943 // __nvvm_read_ptx_sreg_ctaid_x
11944 .{ .tag = @enumFromInt(3386), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11945 // __nvvm_read_ptx_sreg_ctaid_y
11946 .{ .tag = @enumFromInt(3387), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11947 // __nvvm_read_ptx_sreg_ctaid_z
11948 .{ .tag = @enumFromInt(3388), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11949 // __nvvm_read_ptx_sreg_gridid
11950 .{ .tag = @enumFromInt(3389), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11951 // __nvvm_read_ptx_sreg_laneid
11952 .{ .tag = @enumFromInt(3390), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11953 // __nvvm_read_ptx_sreg_lanemask_eq
11954 .{ .tag = @enumFromInt(3391), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11955 // __nvvm_read_ptx_sreg_lanemask_ge
11956 .{ .tag = @enumFromInt(3392), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11957 // __nvvm_read_ptx_sreg_lanemask_gt
11958 .{ .tag = @enumFromInt(3393), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11959 // __nvvm_read_ptx_sreg_lanemask_le
11960 .{ .tag = @enumFromInt(3394), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11961 // __nvvm_read_ptx_sreg_lanemask_lt
11962 .{ .tag = @enumFromInt(3395), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11963 // __nvvm_read_ptx_sreg_nctaid_w
11964 .{ .tag = @enumFromInt(3396), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11965 // __nvvm_read_ptx_sreg_nctaid_x
11966 .{ .tag = @enumFromInt(3397), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11967 // __nvvm_read_ptx_sreg_nctaid_y
11968 .{ .tag = @enumFromInt(3398), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11969 // __nvvm_read_ptx_sreg_nctaid_z
11970 .{ .tag = @enumFromInt(3399), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11971 // __nvvm_read_ptx_sreg_nsmid
11972 .{ .tag = @enumFromInt(3400), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11973 // __nvvm_read_ptx_sreg_ntid_w
11974 .{ .tag = @enumFromInt(3401), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11975 // __nvvm_read_ptx_sreg_ntid_x
11976 .{ .tag = @enumFromInt(3402), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11977 // __nvvm_read_ptx_sreg_ntid_y
11978 .{ .tag = @enumFromInt(3403), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11979 // __nvvm_read_ptx_sreg_ntid_z
11980 .{ .tag = @enumFromInt(3404), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11981 // __nvvm_read_ptx_sreg_nwarpid
11982 .{ .tag = @enumFromInt(3405), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11983 // __nvvm_read_ptx_sreg_pm0
11984 .{ .tag = @enumFromInt(3406), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx) } },
11985 // __nvvm_read_ptx_sreg_pm1
11986 .{ .tag = @enumFromInt(3407), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx) } },
11987 // __nvvm_read_ptx_sreg_pm2
11988 .{ .tag = @enumFromInt(3408), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx) } },
11989 // __nvvm_read_ptx_sreg_pm3
11990 .{ .tag = @enumFromInt(3409), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx) } },
11991 // __nvvm_read_ptx_sreg_smid
11992 .{ .tag = @enumFromInt(3410), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11993 // __nvvm_read_ptx_sreg_tid_w
11994 .{ .tag = @enumFromInt(3411), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11995 // __nvvm_read_ptx_sreg_tid_x
11996 .{ .tag = @enumFromInt(3412), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11997 // __nvvm_read_ptx_sreg_tid_y
11998 .{ .tag = @enumFromInt(3413), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
11999 // __nvvm_read_ptx_sreg_tid_z
12000 .{ .tag = @enumFromInt(3414), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
12001 // __nvvm_read_ptx_sreg_warpid
12002 .{ .tag = @enumFromInt(3415), .properties = .{ .param_str = "i", .target_set = TargetSet.initOne(.nvptx), .attributes = .{ .@"const" = true } } },
12003 // __nvvm_round_d
12004 .{ .tag = @enumFromInt(3416), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
12005 // __nvvm_round_f
12006 .{ .tag = @enumFromInt(3417), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12007 // __nvvm_round_ftz_f
12008 .{ .tag = @enumFromInt(3418), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12009 // __nvvm_rsqrt_approx_d
12010 .{ .tag = @enumFromInt(3419), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
12011 // __nvvm_rsqrt_approx_f
12012 .{ .tag = @enumFromInt(3420), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12013 // __nvvm_rsqrt_approx_ftz_f
12014 .{ .tag = @enumFromInt(3421), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12015 // __nvvm_sad_i
12016 .{ .tag = @enumFromInt(3422), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.nvptx) } },
12017 // __nvvm_sad_ui
12018 .{ .tag = @enumFromInt(3423), .properties = .{ .param_str = "UiUiUiUi", .target_set = TargetSet.initOne(.nvptx) } },
12019 // __nvvm_saturate_d
12020 .{ .tag = @enumFromInt(3424), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
12021 // __nvvm_saturate_f
12022 .{ .tag = @enumFromInt(3425), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12023 // __nvvm_saturate_ftz_f
12024 .{ .tag = @enumFromInt(3426), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12025 // __nvvm_shfl_bfly_f32
12026 .{ .tag = @enumFromInt(3427), .properties = .{ .param_str = "ffii", .target_set = TargetSet.initOne(.nvptx) } },
12027 // __nvvm_shfl_bfly_i32
12028 .{ .tag = @enumFromInt(3428), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.nvptx) } },
12029 // __nvvm_shfl_down_f32
12030 .{ .tag = @enumFromInt(3429), .properties = .{ .param_str = "ffii", .target_set = TargetSet.initOne(.nvptx) } },
12031 // __nvvm_shfl_down_i32
12032 .{ .tag = @enumFromInt(3430), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.nvptx) } },
12033 // __nvvm_shfl_idx_f32
12034 .{ .tag = @enumFromInt(3431), .properties = .{ .param_str = "ffii", .target_set = TargetSet.initOne(.nvptx) } },
12035 // __nvvm_shfl_idx_i32
12036 .{ .tag = @enumFromInt(3432), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.nvptx) } },
12037 // __nvvm_shfl_up_f32
12038 .{ .tag = @enumFromInt(3433), .properties = .{ .param_str = "ffii", .target_set = TargetSet.initOne(.nvptx) } },
12039 // __nvvm_shfl_up_i32
12040 .{ .tag = @enumFromInt(3434), .properties = .{ .param_str = "iiii", .target_set = TargetSet.initOne(.nvptx) } },
12041 // __nvvm_sin_approx_f
12042 .{ .tag = @enumFromInt(3435), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12043 // __nvvm_sin_approx_ftz_f
12044 .{ .tag = @enumFromInt(3436), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12045 // __nvvm_sqrt_approx_f
12046 .{ .tag = @enumFromInt(3437), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12047 // __nvvm_sqrt_approx_ftz_f
12048 .{ .tag = @enumFromInt(3438), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12049 // __nvvm_sqrt_rm_d
12050 .{ .tag = @enumFromInt(3439), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
12051 // __nvvm_sqrt_rm_f
12052 .{ .tag = @enumFromInt(3440), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12053 // __nvvm_sqrt_rm_ftz_f
12054 .{ .tag = @enumFromInt(3441), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12055 // __nvvm_sqrt_rn_d
12056 .{ .tag = @enumFromInt(3442), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
12057 // __nvvm_sqrt_rn_f
12058 .{ .tag = @enumFromInt(3443), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12059 // __nvvm_sqrt_rn_ftz_f
12060 .{ .tag = @enumFromInt(3444), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12061 // __nvvm_sqrt_rp_d
12062 .{ .tag = @enumFromInt(3445), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
12063 // __nvvm_sqrt_rp_f
12064 .{ .tag = @enumFromInt(3446), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12065 // __nvvm_sqrt_rp_ftz_f
12066 .{ .tag = @enumFromInt(3447), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12067 // __nvvm_sqrt_rz_d
12068 .{ .tag = @enumFromInt(3448), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
12069 // __nvvm_sqrt_rz_f
12070 .{ .tag = @enumFromInt(3449), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12071 // __nvvm_sqrt_rz_ftz_f
12072 .{ .tag = @enumFromInt(3450), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12073 // __nvvm_trunc_d
12074 .{ .tag = @enumFromInt(3451), .properties = .{ .param_str = "dd", .target_set = TargetSet.initOne(.nvptx) } },
12075 // __nvvm_trunc_f
12076 .{ .tag = @enumFromInt(3452), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12077 // __nvvm_trunc_ftz_f
12078 .{ .tag = @enumFromInt(3453), .properties = .{ .param_str = "ff", .target_set = TargetSet.initOne(.nvptx) } },
12079 // __nvvm_ui2d_rm
12080 .{ .tag = @enumFromInt(3454), .properties = .{ .param_str = "dUi", .target_set = TargetSet.initOne(.nvptx) } },
12081 // __nvvm_ui2d_rn
12082 .{ .tag = @enumFromInt(3455), .properties = .{ .param_str = "dUi", .target_set = TargetSet.initOne(.nvptx) } },
12083 // __nvvm_ui2d_rp
12084 .{ .tag = @enumFromInt(3456), .properties = .{ .param_str = "dUi", .target_set = TargetSet.initOne(.nvptx) } },
12085 // __nvvm_ui2d_rz
12086 .{ .tag = @enumFromInt(3457), .properties = .{ .param_str = "dUi", .target_set = TargetSet.initOne(.nvptx) } },
12087 // __nvvm_ui2f_rm
12088 .{ .tag = @enumFromInt(3458), .properties = .{ .param_str = "fUi", .target_set = TargetSet.initOne(.nvptx) } },
12089 // __nvvm_ui2f_rn
12090 .{ .tag = @enumFromInt(3459), .properties = .{ .param_str = "fUi", .target_set = TargetSet.initOne(.nvptx) } },
12091 // __nvvm_ui2f_rp
12092 .{ .tag = @enumFromInt(3460), .properties = .{ .param_str = "fUi", .target_set = TargetSet.initOne(.nvptx) } },
12093 // __nvvm_ui2f_rz
12094 .{ .tag = @enumFromInt(3461), .properties = .{ .param_str = "fUi", .target_set = TargetSet.initOne(.nvptx) } },
12095 // __nvvm_ull2d_rm
12096 .{ .tag = @enumFromInt(3462), .properties = .{ .param_str = "dULLi", .target_set = TargetSet.initOne(.nvptx) } },
12097 // __nvvm_ull2d_rn
12098 .{ .tag = @enumFromInt(3463), .properties = .{ .param_str = "dULLi", .target_set = TargetSet.initOne(.nvptx) } },
12099 // __nvvm_ull2d_rp
12100 .{ .tag = @enumFromInt(3464), .properties = .{ .param_str = "dULLi", .target_set = TargetSet.initOne(.nvptx) } },
12101 // __nvvm_ull2d_rz
12102 .{ .tag = @enumFromInt(3465), .properties = .{ .param_str = "dULLi", .target_set = TargetSet.initOne(.nvptx) } },
12103 // __nvvm_ull2f_rm
12104 .{ .tag = @enumFromInt(3466), .properties = .{ .param_str = "fULLi", .target_set = TargetSet.initOne(.nvptx) } },
12105 // __nvvm_ull2f_rn
12106 .{ .tag = @enumFromInt(3467), .properties = .{ .param_str = "fULLi", .target_set = TargetSet.initOne(.nvptx) } },
12107 // __nvvm_ull2f_rp
12108 .{ .tag = @enumFromInt(3468), .properties = .{ .param_str = "fULLi", .target_set = TargetSet.initOne(.nvptx) } },
12109 // __nvvm_ull2f_rz
12110 .{ .tag = @enumFromInt(3469), .properties = .{ .param_str = "fULLi", .target_set = TargetSet.initOne(.nvptx) } },
12111 // __nvvm_vote_all
12112 .{ .tag = @enumFromInt(3470), .properties = .{ .param_str = "bb", .target_set = TargetSet.initOne(.nvptx) } },
12113 // __nvvm_vote_any
12114 .{ .tag = @enumFromInt(3471), .properties = .{ .param_str = "bb", .target_set = TargetSet.initOne(.nvptx) } },
12115 // __nvvm_vote_ballot
12116 .{ .tag = @enumFromInt(3472), .properties = .{ .param_str = "Uib", .target_set = TargetSet.initOne(.nvptx) } },
12117 // __nvvm_vote_uni
12118 .{ .tag = @enumFromInt(3473), .properties = .{ .param_str = "bb", .target_set = TargetSet.initOne(.nvptx) } },
12119 // __popcnt
12120 .{ .tag = @enumFromInt(3474), .properties = .{ .param_str = "UiUi", .language = .all_ms_languages, .attributes = .{ .@"const" = true, .const_evaluable = true } } },
12121 // __popcnt16
12122 .{ .tag = @enumFromInt(3475), .properties = .{ .param_str = "UsUs", .language = .all_ms_languages, .attributes = .{ .@"const" = true, .const_evaluable = true } } },
12123 // __popcnt64
12124 .{ .tag = @enumFromInt(3476), .properties = .{ .param_str = "UWiUWi", .language = .all_ms_languages, .attributes = .{ .@"const" = true, .const_evaluable = true } } },
12125 // __rdtsc
12126 .{ .tag = @enumFromInt(3477), .properties = .{ .param_str = "UOi", .target_set = TargetSet.initOne(.x86) } },
12127 // __sev
12128 .{ .tag = @enumFromInt(3478), .properties = .{ .param_str = "v", .language = .all_ms_languages, .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
12129 // __sevl
12130 .{ .tag = @enumFromInt(3479), .properties = .{ .param_str = "v", .language = .all_ms_languages, .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
12131 // __sigsetjmp
12132 .{ .tag = @enumFromInt(3480), .properties = .{ .param_str = "iSJi", .header = .setjmp, .attributes = .{ .allow_type_mismatch = true, .lib_function_without_prefix = true, .returns_twice = true } } },
12133 // __sinpi
12134 .{ .tag = @enumFromInt(3481), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12135 // __sinpif
12136 .{ .tag = @enumFromInt(3482), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12137 // __sync_add_and_fetch
12138 .{ .tag = @enumFromInt(3483), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12139 // __sync_add_and_fetch_1
12140 .{ .tag = @enumFromInt(3484), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12141 // __sync_add_and_fetch_16
12142 .{ .tag = @enumFromInt(3485), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12143 // __sync_add_and_fetch_2
12144 .{ .tag = @enumFromInt(3486), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12145 // __sync_add_and_fetch_4
12146 .{ .tag = @enumFromInt(3487), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12147 // __sync_add_and_fetch_8
12148 .{ .tag = @enumFromInt(3488), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12149 // __sync_and_and_fetch
12150 .{ .tag = @enumFromInt(3489), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12151 // __sync_and_and_fetch_1
12152 .{ .tag = @enumFromInt(3490), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12153 // __sync_and_and_fetch_16
12154 .{ .tag = @enumFromInt(3491), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12155 // __sync_and_and_fetch_2
12156 .{ .tag = @enumFromInt(3492), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12157 // __sync_and_and_fetch_4
12158 .{ .tag = @enumFromInt(3493), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12159 // __sync_and_and_fetch_8
12160 .{ .tag = @enumFromInt(3494), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12161 // __sync_bool_compare_and_swap
12162 .{ .tag = @enumFromInt(3495), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12163 // __sync_bool_compare_and_swap_1
12164 .{ .tag = @enumFromInt(3496), .properties = .{ .param_str = "bcD*cc.", .attributes = .{ .custom_typecheck = true } } },
12165 // __sync_bool_compare_and_swap_16
12166 .{ .tag = @enumFromInt(3497), .properties = .{ .param_str = "bLLLiD*LLLiLLLi.", .attributes = .{ .custom_typecheck = true } } },
12167 // __sync_bool_compare_and_swap_2
12168 .{ .tag = @enumFromInt(3498), .properties = .{ .param_str = "bsD*ss.", .attributes = .{ .custom_typecheck = true } } },
12169 // __sync_bool_compare_and_swap_4
12170 .{ .tag = @enumFromInt(3499), .properties = .{ .param_str = "biD*ii.", .attributes = .{ .custom_typecheck = true } } },
12171 // __sync_bool_compare_and_swap_8
12172 .{ .tag = @enumFromInt(3500), .properties = .{ .param_str = "bLLiD*LLiLLi.", .attributes = .{ .custom_typecheck = true } } },
12173 // __sync_fetch_and_add
12174 .{ .tag = @enumFromInt(3501), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12175 // __sync_fetch_and_add_1
12176 .{ .tag = @enumFromInt(3502), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12177 // __sync_fetch_and_add_16
12178 .{ .tag = @enumFromInt(3503), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12179 // __sync_fetch_and_add_2
12180 .{ .tag = @enumFromInt(3504), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12181 // __sync_fetch_and_add_4
12182 .{ .tag = @enumFromInt(3505), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12183 // __sync_fetch_and_add_8
12184 .{ .tag = @enumFromInt(3506), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12185 // __sync_fetch_and_and
12186 .{ .tag = @enumFromInt(3507), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12187 // __sync_fetch_and_and_1
12188 .{ .tag = @enumFromInt(3508), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12189 // __sync_fetch_and_and_16
12190 .{ .tag = @enumFromInt(3509), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12191 // __sync_fetch_and_and_2
12192 .{ .tag = @enumFromInt(3510), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12193 // __sync_fetch_and_and_4
12194 .{ .tag = @enumFromInt(3511), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12195 // __sync_fetch_and_and_8
12196 .{ .tag = @enumFromInt(3512), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12197 // __sync_fetch_and_max
12198 .{ .tag = @enumFromInt(3513), .properties = .{ .param_str = "iiD*i" } },
12199 // __sync_fetch_and_min
12200 .{ .tag = @enumFromInt(3514), .properties = .{ .param_str = "iiD*i" } },
12201 // __sync_fetch_and_nand
12202 .{ .tag = @enumFromInt(3515), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12203 // __sync_fetch_and_nand_1
12204 .{ .tag = @enumFromInt(3516), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12205 // __sync_fetch_and_nand_16
12206 .{ .tag = @enumFromInt(3517), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12207 // __sync_fetch_and_nand_2
12208 .{ .tag = @enumFromInt(3518), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12209 // __sync_fetch_and_nand_4
12210 .{ .tag = @enumFromInt(3519), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12211 // __sync_fetch_and_nand_8
12212 .{ .tag = @enumFromInt(3520), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12213 // __sync_fetch_and_or
12214 .{ .tag = @enumFromInt(3521), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12215 // __sync_fetch_and_or_1
12216 .{ .tag = @enumFromInt(3522), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12217 // __sync_fetch_and_or_16
12218 .{ .tag = @enumFromInt(3523), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12219 // __sync_fetch_and_or_2
12220 .{ .tag = @enumFromInt(3524), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12221 // __sync_fetch_and_or_4
12222 .{ .tag = @enumFromInt(3525), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12223 // __sync_fetch_and_or_8
12224 .{ .tag = @enumFromInt(3526), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12225 // __sync_fetch_and_sub
12226 .{ .tag = @enumFromInt(3527), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12227 // __sync_fetch_and_sub_1
12228 .{ .tag = @enumFromInt(3528), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12229 // __sync_fetch_and_sub_16
12230 .{ .tag = @enumFromInt(3529), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12231 // __sync_fetch_and_sub_2
12232 .{ .tag = @enumFromInt(3530), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12233 // __sync_fetch_and_sub_4
12234 .{ .tag = @enumFromInt(3531), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12235 // __sync_fetch_and_sub_8
12236 .{ .tag = @enumFromInt(3532), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12237 // __sync_fetch_and_umax
12238 .{ .tag = @enumFromInt(3533), .properties = .{ .param_str = "UiUiD*Ui" } },
12239 // __sync_fetch_and_umin
12240 .{ .tag = @enumFromInt(3534), .properties = .{ .param_str = "UiUiD*Ui" } },
12241 // __sync_fetch_and_xor
12242 .{ .tag = @enumFromInt(3535), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12243 // __sync_fetch_and_xor_1
12244 .{ .tag = @enumFromInt(3536), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12245 // __sync_fetch_and_xor_16
12246 .{ .tag = @enumFromInt(3537), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12247 // __sync_fetch_and_xor_2
12248 .{ .tag = @enumFromInt(3538), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12249 // __sync_fetch_and_xor_4
12250 .{ .tag = @enumFromInt(3539), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12251 // __sync_fetch_and_xor_8
12252 .{ .tag = @enumFromInt(3540), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12253 // __sync_lock_release
12254 .{ .tag = @enumFromInt(3541), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12255 // __sync_lock_release_1
12256 .{ .tag = @enumFromInt(3542), .properties = .{ .param_str = "vcD*.", .attributes = .{ .custom_typecheck = true } } },
12257 // __sync_lock_release_16
12258 .{ .tag = @enumFromInt(3543), .properties = .{ .param_str = "vLLLiD*.", .attributes = .{ .custom_typecheck = true } } },
12259 // __sync_lock_release_2
12260 .{ .tag = @enumFromInt(3544), .properties = .{ .param_str = "vsD*.", .attributes = .{ .custom_typecheck = true } } },
12261 // __sync_lock_release_4
12262 .{ .tag = @enumFromInt(3545), .properties = .{ .param_str = "viD*.", .attributes = .{ .custom_typecheck = true } } },
12263 // __sync_lock_release_8
12264 .{ .tag = @enumFromInt(3546), .properties = .{ .param_str = "vLLiD*.", .attributes = .{ .custom_typecheck = true } } },
12265 // __sync_lock_test_and_set
12266 .{ .tag = @enumFromInt(3547), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12267 // __sync_lock_test_and_set_1
12268 .{ .tag = @enumFromInt(3548), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12269 // __sync_lock_test_and_set_16
12270 .{ .tag = @enumFromInt(3549), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12271 // __sync_lock_test_and_set_2
12272 .{ .tag = @enumFromInt(3550), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12273 // __sync_lock_test_and_set_4
12274 .{ .tag = @enumFromInt(3551), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12275 // __sync_lock_test_and_set_8
12276 .{ .tag = @enumFromInt(3552), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12277 // __sync_nand_and_fetch
12278 .{ .tag = @enumFromInt(3553), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12279 // __sync_nand_and_fetch_1
12280 .{ .tag = @enumFromInt(3554), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12281 // __sync_nand_and_fetch_16
12282 .{ .tag = @enumFromInt(3555), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12283 // __sync_nand_and_fetch_2
12284 .{ .tag = @enumFromInt(3556), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12285 // __sync_nand_and_fetch_4
12286 .{ .tag = @enumFromInt(3557), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12287 // __sync_nand_and_fetch_8
12288 .{ .tag = @enumFromInt(3558), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12289 // __sync_or_and_fetch
12290 .{ .tag = @enumFromInt(3559), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12291 // __sync_or_and_fetch_1
12292 .{ .tag = @enumFromInt(3560), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12293 // __sync_or_and_fetch_16
12294 .{ .tag = @enumFromInt(3561), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12295 // __sync_or_and_fetch_2
12296 .{ .tag = @enumFromInt(3562), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12297 // __sync_or_and_fetch_4
12298 .{ .tag = @enumFromInt(3563), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12299 // __sync_or_and_fetch_8
12300 .{ .tag = @enumFromInt(3564), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12301 // __sync_sub_and_fetch
12302 .{ .tag = @enumFromInt(3565), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12303 // __sync_sub_and_fetch_1
12304 .{ .tag = @enumFromInt(3566), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12305 // __sync_sub_and_fetch_16
12306 .{ .tag = @enumFromInt(3567), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12307 // __sync_sub_and_fetch_2
12308 .{ .tag = @enumFromInt(3568), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12309 // __sync_sub_and_fetch_4
12310 .{ .tag = @enumFromInt(3569), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12311 // __sync_sub_and_fetch_8
12312 .{ .tag = @enumFromInt(3570), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12313 // __sync_swap
12314 .{ .tag = @enumFromInt(3571), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12315 // __sync_swap_1
12316 .{ .tag = @enumFromInt(3572), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12317 // __sync_swap_16
12318 .{ .tag = @enumFromInt(3573), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12319 // __sync_swap_2
12320 .{ .tag = @enumFromInt(3574), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12321 // __sync_swap_4
12322 .{ .tag = @enumFromInt(3575), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12323 // __sync_swap_8
12324 .{ .tag = @enumFromInt(3576), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12325 // __sync_synchronize
12326 .{ .tag = @enumFromInt(3577), .properties = .{ .param_str = "v" } },
12327 // __sync_val_compare_and_swap
12328 .{ .tag = @enumFromInt(3578), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12329 // __sync_val_compare_and_swap_1
12330 .{ .tag = @enumFromInt(3579), .properties = .{ .param_str = "ccD*cc.", .attributes = .{ .custom_typecheck = true } } },
12331 // __sync_val_compare_and_swap_16
12332 .{ .tag = @enumFromInt(3580), .properties = .{ .param_str = "LLLiLLLiD*LLLiLLLi.", .attributes = .{ .custom_typecheck = true } } },
12333 // __sync_val_compare_and_swap_2
12334 .{ .tag = @enumFromInt(3581), .properties = .{ .param_str = "ssD*ss.", .attributes = .{ .custom_typecheck = true } } },
12335 // __sync_val_compare_and_swap_4
12336 .{ .tag = @enumFromInt(3582), .properties = .{ .param_str = "iiD*ii.", .attributes = .{ .custom_typecheck = true } } },
12337 // __sync_val_compare_and_swap_8
12338 .{ .tag = @enumFromInt(3583), .properties = .{ .param_str = "LLiLLiD*LLiLLi.", .attributes = .{ .custom_typecheck = true } } },
12339 // __sync_xor_and_fetch
12340 .{ .tag = @enumFromInt(3584), .properties = .{ .param_str = "v.", .attributes = .{ .custom_typecheck = true } } },
12341 // __sync_xor_and_fetch_1
12342 .{ .tag = @enumFromInt(3585), .properties = .{ .param_str = "ccD*c.", .attributes = .{ .custom_typecheck = true } } },
12343 // __sync_xor_and_fetch_16
12344 .{ .tag = @enumFromInt(3586), .properties = .{ .param_str = "LLLiLLLiD*LLLi.", .attributes = .{ .custom_typecheck = true } } },
12345 // __sync_xor_and_fetch_2
12346 .{ .tag = @enumFromInt(3587), .properties = .{ .param_str = "ssD*s.", .attributes = .{ .custom_typecheck = true } } },
12347 // __sync_xor_and_fetch_4
12348 .{ .tag = @enumFromInt(3588), .properties = .{ .param_str = "iiD*i.", .attributes = .{ .custom_typecheck = true } } },
12349 // __sync_xor_and_fetch_8
12350 .{ .tag = @enumFromInt(3589), .properties = .{ .param_str = "LLiLLiD*LLi.", .attributes = .{ .custom_typecheck = true } } },
12351 // __syncthreads
12352 .{ .tag = @enumFromInt(3590), .properties = .{ .param_str = "v", .target_set = TargetSet.initOne(.nvptx) } },
12353 // __tanpi
12354 .{ .tag = @enumFromInt(3591), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12355 // __tanpif
12356 .{ .tag = @enumFromInt(3592), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12357 // __va_start
12358 .{ .tag = @enumFromInt(3593), .properties = .{ .param_str = "vc**.", .language = .all_ms_languages, .attributes = .{ .custom_typecheck = true } } },
12359 // __warn_memset_zero_len
12360 .{ .tag = @enumFromInt(3594), .properties = .{ .param_str = "v", .attributes = .{ .pure = true } } },
12361 // __wfe
12362 .{ .tag = @enumFromInt(3595), .properties = .{ .param_str = "v", .language = .all_ms_languages, .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
12363 // __wfi
12364 .{ .tag = @enumFromInt(3596), .properties = .{ .param_str = "v", .language = .all_ms_languages, .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
12365 // __xray_customevent
12366 .{ .tag = @enumFromInt(3597), .properties = .{ .param_str = "vcC*z" } },
12367 // __xray_typedevent
12368 .{ .tag = @enumFromInt(3598), .properties = .{ .param_str = "vzcC*z" } },
12369 // __yield
12370 .{ .tag = @enumFromInt(3599), .properties = .{ .param_str = "v", .language = .all_ms_languages, .target_set = TargetSet.initMany(&.{ .aarch64, .arm }) } },
12371 // _abnormal_termination
12372 .{ .tag = @enumFromInt(3600), .properties = .{ .param_str = "i", .language = .all_ms_languages } },
12373 // _alloca
12374 .{ .tag = @enumFromInt(3601), .properties = .{ .param_str = "v*z", .language = .all_ms_languages } },
12375 // _bittest
12376 .{ .tag = @enumFromInt(3602), .properties = .{ .param_str = "UcNiC*Ni", .language = .all_ms_languages } },
12377 // _bittest64
12378 .{ .tag = @enumFromInt(3603), .properties = .{ .param_str = "UcWiC*Wi", .language = .all_ms_languages } },
12379 // _bittestandcomplement
12380 .{ .tag = @enumFromInt(3604), .properties = .{ .param_str = "UcNi*Ni", .language = .all_ms_languages } },
12381 // _bittestandcomplement64
12382 .{ .tag = @enumFromInt(3605), .properties = .{ .param_str = "UcWi*Wi", .language = .all_ms_languages } },
12383 // _bittestandreset
12384 .{ .tag = @enumFromInt(3606), .properties = .{ .param_str = "UcNi*Ni", .language = .all_ms_languages } },
12385 // _bittestandreset64
12386 .{ .tag = @enumFromInt(3607), .properties = .{ .param_str = "UcWi*Wi", .language = .all_ms_languages } },
12387 // _bittestandset
12388 .{ .tag = @enumFromInt(3608), .properties = .{ .param_str = "UcNi*Ni", .language = .all_ms_languages } },
12389 // _bittestandset64
12390 .{ .tag = @enumFromInt(3609), .properties = .{ .param_str = "UcWi*Wi", .language = .all_ms_languages } },
12391 // _byteswap_uint64
12392 .{ .tag = @enumFromInt(3610), .properties = .{ .param_str = "ULLiULLi", .header = .stdlib, .language = .all_ms_languages, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12393 // _byteswap_ulong
12394 .{ .tag = @enumFromInt(3611), .properties = .{ .param_str = "UNiUNi", .header = .stdlib, .language = .all_ms_languages, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12395 // _byteswap_ushort
12396 .{ .tag = @enumFromInt(3612), .properties = .{ .param_str = "UsUs", .header = .stdlib, .language = .all_ms_languages, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12397 // _exception_code
12398 .{ .tag = @enumFromInt(3613), .properties = .{ .param_str = "UNi", .language = .all_ms_languages } },
12399 // _exception_info
12400 .{ .tag = @enumFromInt(3614), .properties = .{ .param_str = "v*", .language = .all_ms_languages } },
12401 // _exit
12402 .{ .tag = @enumFromInt(3615), .properties = .{ .param_str = "vi", .header = .unistd, .language = .all_gnu_languages, .attributes = .{ .noreturn = true, .lib_function_without_prefix = true } } },
12403 // _interlockedbittestandreset
12404 .{ .tag = @enumFromInt(3616), .properties = .{ .param_str = "UcNiD*Ni", .language = .all_ms_languages } },
12405 // _interlockedbittestandreset64
12406 .{ .tag = @enumFromInt(3617), .properties = .{ .param_str = "UcWiD*Wi", .language = .all_ms_languages } },
12407 // _interlockedbittestandreset_acq
12408 .{ .tag = @enumFromInt(3618), .properties = .{ .param_str = "UcNiD*Ni", .language = .all_ms_languages } },
12409 // _interlockedbittestandreset_nf
12410 .{ .tag = @enumFromInt(3619), .properties = .{ .param_str = "UcNiD*Ni", .language = .all_ms_languages } },
12411 // _interlockedbittestandreset_rel
12412 .{ .tag = @enumFromInt(3620), .properties = .{ .param_str = "UcNiD*Ni", .language = .all_ms_languages } },
12413 // _interlockedbittestandset
12414 .{ .tag = @enumFromInt(3621), .properties = .{ .param_str = "UcNiD*Ni", .language = .all_ms_languages } },
12415 // _interlockedbittestandset64
12416 .{ .tag = @enumFromInt(3622), .properties = .{ .param_str = "UcWiD*Wi", .language = .all_ms_languages } },
12417 // _interlockedbittestandset_acq
12418 .{ .tag = @enumFromInt(3623), .properties = .{ .param_str = "UcNiD*Ni", .language = .all_ms_languages } },
12419 // _interlockedbittestandset_nf
12420 .{ .tag = @enumFromInt(3624), .properties = .{ .param_str = "UcNiD*Ni", .language = .all_ms_languages } },
12421 // _interlockedbittestandset_rel
12422 .{ .tag = @enumFromInt(3625), .properties = .{ .param_str = "UcNiD*Ni", .language = .all_ms_languages } },
12423 // _longjmp
12424 .{ .tag = @enumFromInt(3626), .properties = .{ .param_str = "vJi", .header = .setjmp, .language = .all_gnu_languages, .attributes = .{ .noreturn = true, .allow_type_mismatch = true, .lib_function_without_prefix = true } } },
12425 // _lrotl
12426 .{ .tag = @enumFromInt(3627), .properties = .{ .param_str = "ULiULii", .language = .all_ms_languages, .attributes = .{ .const_evaluable = true } } },
12427 // _lrotr
12428 .{ .tag = @enumFromInt(3628), .properties = .{ .param_str = "ULiULii", .language = .all_ms_languages, .attributes = .{ .const_evaluable = true } } },
12429 // _rotl
12430 .{ .tag = @enumFromInt(3629), .properties = .{ .param_str = "UiUii", .language = .all_ms_languages, .attributes = .{ .const_evaluable = true } } },
12431 // _rotl16
12432 .{ .tag = @enumFromInt(3630), .properties = .{ .param_str = "UsUsUc", .language = .all_ms_languages, .attributes = .{ .const_evaluable = true } } },
12433 // _rotl64
12434 .{ .tag = @enumFromInt(3631), .properties = .{ .param_str = "UWiUWii", .language = .all_ms_languages, .attributes = .{ .const_evaluable = true } } },
12435 // _rotl8
12436 .{ .tag = @enumFromInt(3632), .properties = .{ .param_str = "UcUcUc", .language = .all_ms_languages, .attributes = .{ .const_evaluable = true } } },
12437 // _rotr
12438 .{ .tag = @enumFromInt(3633), .properties = .{ .param_str = "UiUii", .language = .all_ms_languages, .attributes = .{ .const_evaluable = true } } },
12439 // _rotr16
12440 .{ .tag = @enumFromInt(3634), .properties = .{ .param_str = "UsUsUc", .language = .all_ms_languages, .attributes = .{ .const_evaluable = true } } },
12441 // _rotr64
12442 .{ .tag = @enumFromInt(3635), .properties = .{ .param_str = "UWiUWii", .language = .all_ms_languages, .attributes = .{ .const_evaluable = true } } },
12443 // _rotr8
12444 .{ .tag = @enumFromInt(3636), .properties = .{ .param_str = "UcUcUc", .language = .all_ms_languages, .attributes = .{ .const_evaluable = true } } },
12445 // _setjmp
12446 .{ .tag = @enumFromInt(3637), .properties = .{ .param_str = "iJ", .header = .setjmp, .attributes = .{ .allow_type_mismatch = true, .lib_function_without_prefix = true, .returns_twice = true } } },
12447 // _setjmpex
12448 .{ .tag = @enumFromInt(3638), .properties = .{ .param_str = "iJ", .header = .setjmpex, .language = .all_ms_languages, .attributes = .{ .allow_type_mismatch = true, .lib_function_without_prefix = true, .returns_twice = true } } },
12449 // abort
12450 .{ .tag = @enumFromInt(3639), .properties = .{ .param_str = "v", .header = .stdlib, .attributes = .{ .noreturn = true, .lib_function_without_prefix = true } } },
12451 // abs
12452 .{ .tag = @enumFromInt(3640), .properties = .{ .param_str = "ii", .header = .stdlib, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12453 // acos
12454 .{ .tag = @enumFromInt(3641), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12455 // acosf
12456 .{ .tag = @enumFromInt(3642), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12457 // acosh
12458 .{ .tag = @enumFromInt(3643), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12459 // acoshf
12460 .{ .tag = @enumFromInt(3644), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12461 // acoshl
12462 .{ .tag = @enumFromInt(3645), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12463 // acosl
12464 .{ .tag = @enumFromInt(3646), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12465 // aligned_alloc
12466 .{ .tag = @enumFromInt(3647), .properties = .{ .param_str = "v*zz", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
12467 // alloca
12468 .{ .tag = @enumFromInt(3648), .properties = .{ .param_str = "v*z", .header = .stdlib, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
12469 // asin
12470 .{ .tag = @enumFromInt(3649), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12471 // asinf
12472 .{ .tag = @enumFromInt(3650), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12473 // asinh
12474 .{ .tag = @enumFromInt(3651), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12475 // asinhf
12476 .{ .tag = @enumFromInt(3652), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12477 // asinhl
12478 .{ .tag = @enumFromInt(3653), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12479 // asinl
12480 .{ .tag = @enumFromInt(3654), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12481 // atan
12482 .{ .tag = @enumFromInt(3655), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12483 // atan2
12484 .{ .tag = @enumFromInt(3656), .properties = .{ .param_str = "ddd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12485 // atan2f
12486 .{ .tag = @enumFromInt(3657), .properties = .{ .param_str = "fff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12487 // atan2l
12488 .{ .tag = @enumFromInt(3658), .properties = .{ .param_str = "LdLdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12489 // atanf
12490 .{ .tag = @enumFromInt(3659), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12491 // atanh
12492 .{ .tag = @enumFromInt(3660), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12493 // atanhf
12494 .{ .tag = @enumFromInt(3661), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12495 // atanhl
12496 .{ .tag = @enumFromInt(3662), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12497 // atanl
12498 .{ .tag = @enumFromInt(3663), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12499 // bcmp
12500 .{ .tag = @enumFromInt(3664), .properties = .{ .param_str = "ivC*vC*z", .header = .strings, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
12501 // bcopy
12502 .{ .tag = @enumFromInt(3665), .properties = .{ .param_str = "vvC*v*z", .header = .strings, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
12503 // bzero
12504 .{ .tag = @enumFromInt(3666), .properties = .{ .param_str = "vv*z", .header = .strings, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
12505 // cabs
12506 .{ .tag = @enumFromInt(3667), .properties = .{ .param_str = "dXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12507 // cabsf
12508 .{ .tag = @enumFromInt(3668), .properties = .{ .param_str = "fXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12509 // cabsl
12510 .{ .tag = @enumFromInt(3669), .properties = .{ .param_str = "LdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12511 // cacos
12512 .{ .tag = @enumFromInt(3670), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12513 // cacosf
12514 .{ .tag = @enumFromInt(3671), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12515 // cacosh
12516 .{ .tag = @enumFromInt(3672), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12517 // cacoshf
12518 .{ .tag = @enumFromInt(3673), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12519 // cacoshl
12520 .{ .tag = @enumFromInt(3674), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12521 // cacosl
12522 .{ .tag = @enumFromInt(3675), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12523 // calloc
12524 .{ .tag = @enumFromInt(3676), .properties = .{ .param_str = "v*zz", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
12525 // carg
12526 .{ .tag = @enumFromInt(3677), .properties = .{ .param_str = "dXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12527 // cargf
12528 .{ .tag = @enumFromInt(3678), .properties = .{ .param_str = "fXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12529 // cargl
12530 .{ .tag = @enumFromInt(3679), .properties = .{ .param_str = "LdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12531 // casin
12532 .{ .tag = @enumFromInt(3680), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12533 // casinf
12534 .{ .tag = @enumFromInt(3681), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12535 // casinh
12536 .{ .tag = @enumFromInt(3682), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12537 // casinhf
12538 .{ .tag = @enumFromInt(3683), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12539 // casinhl
12540 .{ .tag = @enumFromInt(3684), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12541 // casinl
12542 .{ .tag = @enumFromInt(3685), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12543 // catan
12544 .{ .tag = @enumFromInt(3686), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12545 // catanf
12546 .{ .tag = @enumFromInt(3687), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12547 // catanh
12548 .{ .tag = @enumFromInt(3688), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12549 // catanhf
12550 .{ .tag = @enumFromInt(3689), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12551 // catanhl
12552 .{ .tag = @enumFromInt(3690), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12553 // catanl
12554 .{ .tag = @enumFromInt(3691), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12555 // cbrt
12556 .{ .tag = @enumFromInt(3692), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12557 // cbrtf
12558 .{ .tag = @enumFromInt(3693), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12559 // cbrtl
12560 .{ .tag = @enumFromInt(3694), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12561 // ccos
12562 .{ .tag = @enumFromInt(3695), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12563 // ccosf
12564 .{ .tag = @enumFromInt(3696), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12565 // ccosh
12566 .{ .tag = @enumFromInt(3697), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12567 // ccoshf
12568 .{ .tag = @enumFromInt(3698), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12569 // ccoshl
12570 .{ .tag = @enumFromInt(3699), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12571 // ccosl
12572 .{ .tag = @enumFromInt(3700), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12573 // ceil
12574 .{ .tag = @enumFromInt(3701), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12575 // ceilf
12576 .{ .tag = @enumFromInt(3702), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12577 // ceill
12578 .{ .tag = @enumFromInt(3703), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12579 // cexp
12580 .{ .tag = @enumFromInt(3704), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12581 // cexpf
12582 .{ .tag = @enumFromInt(3705), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12583 // cexpl
12584 .{ .tag = @enumFromInt(3706), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12585 // cimag
12586 .{ .tag = @enumFromInt(3707), .properties = .{ .param_str = "dXd", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12587 // cimagf
12588 .{ .tag = @enumFromInt(3708), .properties = .{ .param_str = "fXf", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12589 // cimagl
12590 .{ .tag = @enumFromInt(3709), .properties = .{ .param_str = "LdXLd", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12591 // clog
12592 .{ .tag = @enumFromInt(3710), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12593 // clogf
12594 .{ .tag = @enumFromInt(3711), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12595 // clogl
12596 .{ .tag = @enumFromInt(3712), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12597 // conj
12598 .{ .tag = @enumFromInt(3713), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12599 // conjf
12600 .{ .tag = @enumFromInt(3714), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12601 // conjl
12602 .{ .tag = @enumFromInt(3715), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12603 // copysign
12604 .{ .tag = @enumFromInt(3716), .properties = .{ .param_str = "ddd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12605 // copysignf
12606 .{ .tag = @enumFromInt(3717), .properties = .{ .param_str = "fff", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12607 // copysignl
12608 .{ .tag = @enumFromInt(3718), .properties = .{ .param_str = "LdLdLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12609 // cos
12610 .{ .tag = @enumFromInt(3719), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12611 // cosf
12612 .{ .tag = @enumFromInt(3720), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12613 // cosh
12614 .{ .tag = @enumFromInt(3721), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12615 // coshf
12616 .{ .tag = @enumFromInt(3722), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12617 // coshl
12618 .{ .tag = @enumFromInt(3723), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12619 // cosl
12620 .{ .tag = @enumFromInt(3724), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12621 // cpow
12622 .{ .tag = @enumFromInt(3725), .properties = .{ .param_str = "XdXdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12623 // cpowf
12624 .{ .tag = @enumFromInt(3726), .properties = .{ .param_str = "XfXfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12625 // cpowl
12626 .{ .tag = @enumFromInt(3727), .properties = .{ .param_str = "XLdXLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12627 // cproj
12628 .{ .tag = @enumFromInt(3728), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12629 // cprojf
12630 .{ .tag = @enumFromInt(3729), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12631 // cprojl
12632 .{ .tag = @enumFromInt(3730), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12633 // creal
12634 .{ .tag = @enumFromInt(3731), .properties = .{ .param_str = "dXd", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12635 // crealf
12636 .{ .tag = @enumFromInt(3732), .properties = .{ .param_str = "fXf", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12637 // creall
12638 .{ .tag = @enumFromInt(3733), .properties = .{ .param_str = "LdXLd", .header = .complex, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12639 // csin
12640 .{ .tag = @enumFromInt(3734), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12641 // csinf
12642 .{ .tag = @enumFromInt(3735), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12643 // csinh
12644 .{ .tag = @enumFromInt(3736), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12645 // csinhf
12646 .{ .tag = @enumFromInt(3737), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12647 // csinhl
12648 .{ .tag = @enumFromInt(3738), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12649 // csinl
12650 .{ .tag = @enumFromInt(3739), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12651 // csqrt
12652 .{ .tag = @enumFromInt(3740), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12653 // csqrtf
12654 .{ .tag = @enumFromInt(3741), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12655 // csqrtl
12656 .{ .tag = @enumFromInt(3742), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12657 // ctan
12658 .{ .tag = @enumFromInt(3743), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12659 // ctanf
12660 .{ .tag = @enumFromInt(3744), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12661 // ctanh
12662 .{ .tag = @enumFromInt(3745), .properties = .{ .param_str = "XdXd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12663 // ctanhf
12664 .{ .tag = @enumFromInt(3746), .properties = .{ .param_str = "XfXf", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12665 // ctanhl
12666 .{ .tag = @enumFromInt(3747), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12667 // ctanl
12668 .{ .tag = @enumFromInt(3748), .properties = .{ .param_str = "XLdXLd", .header = .complex, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12669 // erf
12670 .{ .tag = @enumFromInt(3749), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12671 // erfc
12672 .{ .tag = @enumFromInt(3750), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12673 // erfcf
12674 .{ .tag = @enumFromInt(3751), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12675 // erfcl
12676 .{ .tag = @enumFromInt(3752), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12677 // erff
12678 .{ .tag = @enumFromInt(3753), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12679 // erfl
12680 .{ .tag = @enumFromInt(3754), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12681 // exit
12682 .{ .tag = @enumFromInt(3755), .properties = .{ .param_str = "vi", .header = .stdlib, .attributes = .{ .noreturn = true, .lib_function_without_prefix = true } } },
12683 // exp
12684 .{ .tag = @enumFromInt(3756), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12685 // exp2
12686 .{ .tag = @enumFromInt(3757), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12687 // exp2f
12688 .{ .tag = @enumFromInt(3758), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12689 // exp2l
12690 .{ .tag = @enumFromInt(3759), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12691 // expf
12692 .{ .tag = @enumFromInt(3760), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12693 // expl
12694 .{ .tag = @enumFromInt(3761), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12695 // expm1
12696 .{ .tag = @enumFromInt(3762), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12697 // expm1f
12698 .{ .tag = @enumFromInt(3763), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12699 // expm1l
12700 .{ .tag = @enumFromInt(3764), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12701 // fabs
12702 .{ .tag = @enumFromInt(3765), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12703 // fabsf
12704 .{ .tag = @enumFromInt(3766), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12705 // fabsl
12706 .{ .tag = @enumFromInt(3767), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12707 // fdim
12708 .{ .tag = @enumFromInt(3768), .properties = .{ .param_str = "ddd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12709 // fdimf
12710 .{ .tag = @enumFromInt(3769), .properties = .{ .param_str = "fff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12711 // fdiml
12712 .{ .tag = @enumFromInt(3770), .properties = .{ .param_str = "LdLdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12713 // finite
12714 .{ .tag = @enumFromInt(3771), .properties = .{ .param_str = "id", .header = .math, .language = .gnu_lang, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12715 // finitef
12716 .{ .tag = @enumFromInt(3772), .properties = .{ .param_str = "if", .header = .math, .language = .gnu_lang, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12717 // finitel
12718 .{ .tag = @enumFromInt(3773), .properties = .{ .param_str = "iLd", .header = .math, .language = .gnu_lang, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12719 // floor
12720 .{ .tag = @enumFromInt(3774), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12721 // floorf
12722 .{ .tag = @enumFromInt(3775), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12723 // floorl
12724 .{ .tag = @enumFromInt(3776), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12725 // fma
12726 .{ .tag = @enumFromInt(3777), .properties = .{ .param_str = "dddd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12727 // fmaf
12728 .{ .tag = @enumFromInt(3778), .properties = .{ .param_str = "ffff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12729 // fmal
12730 .{ .tag = @enumFromInt(3779), .properties = .{ .param_str = "LdLdLdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12731 // fmax
12732 .{ .tag = @enumFromInt(3780), .properties = .{ .param_str = "ddd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12733 // fmaxf
12734 .{ .tag = @enumFromInt(3781), .properties = .{ .param_str = "fff", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12735 // fmaxl
12736 .{ .tag = @enumFromInt(3782), .properties = .{ .param_str = "LdLdLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12737 // fmin
12738 .{ .tag = @enumFromInt(3783), .properties = .{ .param_str = "ddd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12739 // fminf
12740 .{ .tag = @enumFromInt(3784), .properties = .{ .param_str = "fff", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12741 // fminl
12742 .{ .tag = @enumFromInt(3785), .properties = .{ .param_str = "LdLdLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12743 // fmod
12744 .{ .tag = @enumFromInt(3786), .properties = .{ .param_str = "ddd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12745 // fmodf
12746 .{ .tag = @enumFromInt(3787), .properties = .{ .param_str = "fff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12747 // fmodl
12748 .{ .tag = @enumFromInt(3788), .properties = .{ .param_str = "LdLdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12749 // fopen
12750 .{ .tag = @enumFromInt(3789), .properties = .{ .param_str = "P*cC*cC*", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true } } },
12751 // fprintf
12752 .{ .tag = @enumFromInt(3790), .properties = .{ .param_str = "iP*cC*.", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .printf, .format_string_position = 1 } } },
12753 // fread
12754 .{ .tag = @enumFromInt(3791), .properties = .{ .param_str = "zv*zzP*", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true } } },
12755 // free
12756 .{ .tag = @enumFromInt(3792), .properties = .{ .param_str = "vv*", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
12757 // frexp
12758 .{ .tag = @enumFromInt(3793), .properties = .{ .param_str = "ddi*", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12759 // frexpf
12760 .{ .tag = @enumFromInt(3794), .properties = .{ .param_str = "ffi*", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12761 // frexpl
12762 .{ .tag = @enumFromInt(3795), .properties = .{ .param_str = "LdLdi*", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12763 // fscanf
12764 .{ .tag = @enumFromInt(3796), .properties = .{ .param_str = "iP*RcC*R.", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .scanf, .format_string_position = 1 } } },
12765 // fwrite
12766 .{ .tag = @enumFromInt(3797), .properties = .{ .param_str = "zvC*zzP*", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true } } },
12767 // getcontext
12768 .{ .tag = @enumFromInt(3798), .properties = .{ .param_str = "iK*", .header = .setjmp, .attributes = .{ .allow_type_mismatch = true, .lib_function_without_prefix = true, .returns_twice = true } } },
12769 // hypot
12770 .{ .tag = @enumFromInt(3799), .properties = .{ .param_str = "ddd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12771 // hypotf
12772 .{ .tag = @enumFromInt(3800), .properties = .{ .param_str = "fff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12773 // hypotl
12774 .{ .tag = @enumFromInt(3801), .properties = .{ .param_str = "LdLdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12775 // ilogb
12776 .{ .tag = @enumFromInt(3802), .properties = .{ .param_str = "id", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12777 // ilogbf
12778 .{ .tag = @enumFromInt(3803), .properties = .{ .param_str = "if", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12779 // ilogbl
12780 .{ .tag = @enumFromInt(3804), .properties = .{ .param_str = "iLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12781 // index
12782 .{ .tag = @enumFromInt(3805), .properties = .{ .param_str = "c*cC*i", .header = .strings, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
12783 // isalnum
12784 .{ .tag = @enumFromInt(3806), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12785 // isalpha
12786 .{ .tag = @enumFromInt(3807), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12787 // isblank
12788 .{ .tag = @enumFromInt(3808), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12789 // iscntrl
12790 .{ .tag = @enumFromInt(3809), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12791 // isdigit
12792 .{ .tag = @enumFromInt(3810), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12793 // isgraph
12794 .{ .tag = @enumFromInt(3811), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12795 // islower
12796 .{ .tag = @enumFromInt(3812), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12797 // isprint
12798 .{ .tag = @enumFromInt(3813), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12799 // ispunct
12800 .{ .tag = @enumFromInt(3814), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12801 // isspace
12802 .{ .tag = @enumFromInt(3815), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12803 // isupper
12804 .{ .tag = @enumFromInt(3816), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12805 // isxdigit
12806 .{ .tag = @enumFromInt(3817), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12807 // labs
12808 .{ .tag = @enumFromInt(3818), .properties = .{ .param_str = "LiLi", .header = .stdlib, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12809 // ldexp
12810 .{ .tag = @enumFromInt(3819), .properties = .{ .param_str = "ddi", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12811 // ldexpf
12812 .{ .tag = @enumFromInt(3820), .properties = .{ .param_str = "ffi", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12813 // ldexpl
12814 .{ .tag = @enumFromInt(3821), .properties = .{ .param_str = "LdLdi", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12815 // lgamma
12816 .{ .tag = @enumFromInt(3822), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12817 // lgammaf
12818 .{ .tag = @enumFromInt(3823), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12819 // lgammal
12820 .{ .tag = @enumFromInt(3824), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12821 // llabs
12822 .{ .tag = @enumFromInt(3825), .properties = .{ .param_str = "LLiLLi", .header = .stdlib, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12823 // llrint
12824 .{ .tag = @enumFromInt(3826), .properties = .{ .param_str = "LLid", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12825 // llrintf
12826 .{ .tag = @enumFromInt(3827), .properties = .{ .param_str = "LLif", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12827 // llrintl
12828 .{ .tag = @enumFromInt(3828), .properties = .{ .param_str = "LLiLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12829 // llround
12830 .{ .tag = @enumFromInt(3829), .properties = .{ .param_str = "LLid", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12831 // llroundf
12832 .{ .tag = @enumFromInt(3830), .properties = .{ .param_str = "LLif", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12833 // llroundl
12834 .{ .tag = @enumFromInt(3831), .properties = .{ .param_str = "LLiLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12835 // log
12836 .{ .tag = @enumFromInt(3832), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12837 // log10
12838 .{ .tag = @enumFromInt(3833), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12839 // log10f
12840 .{ .tag = @enumFromInt(3834), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12841 // log10l
12842 .{ .tag = @enumFromInt(3835), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12843 // log1p
12844 .{ .tag = @enumFromInt(3836), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12845 // log1pf
12846 .{ .tag = @enumFromInt(3837), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12847 // log1pl
12848 .{ .tag = @enumFromInt(3838), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12849 // log2
12850 .{ .tag = @enumFromInt(3839), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12851 // log2f
12852 .{ .tag = @enumFromInt(3840), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12853 // log2l
12854 .{ .tag = @enumFromInt(3841), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12855 // logb
12856 .{ .tag = @enumFromInt(3842), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12857 // logbf
12858 .{ .tag = @enumFromInt(3843), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12859 // logbl
12860 .{ .tag = @enumFromInt(3844), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12861 // logf
12862 .{ .tag = @enumFromInt(3845), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12863 // logl
12864 .{ .tag = @enumFromInt(3846), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12865 // longjmp
12866 .{ .tag = @enumFromInt(3847), .properties = .{ .param_str = "vJi", .header = .setjmp, .attributes = .{ .noreturn = true, .allow_type_mismatch = true, .lib_function_without_prefix = true } } },
12867 // lrint
12868 .{ .tag = @enumFromInt(3848), .properties = .{ .param_str = "Lid", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12869 // lrintf
12870 .{ .tag = @enumFromInt(3849), .properties = .{ .param_str = "Lif", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12871 // lrintl
12872 .{ .tag = @enumFromInt(3850), .properties = .{ .param_str = "LiLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12873 // lround
12874 .{ .tag = @enumFromInt(3851), .properties = .{ .param_str = "Lid", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12875 // lroundf
12876 .{ .tag = @enumFromInt(3852), .properties = .{ .param_str = "Lif", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12877 // lroundl
12878 .{ .tag = @enumFromInt(3853), .properties = .{ .param_str = "LiLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12879 // malloc
12880 .{ .tag = @enumFromInt(3854), .properties = .{ .param_str = "v*z", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
12881 // memalign
12882 .{ .tag = @enumFromInt(3855), .properties = .{ .param_str = "v*zz", .header = .malloc, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
12883 // memccpy
12884 .{ .tag = @enumFromInt(3856), .properties = .{ .param_str = "v*v*vC*iz", .header = .string, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
12885 // memchr
12886 .{ .tag = @enumFromInt(3857), .properties = .{ .param_str = "v*vC*iz", .header = .string, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
12887 // memcmp
12888 .{ .tag = @enumFromInt(3858), .properties = .{ .param_str = "ivC*vC*z", .header = .string, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
12889 // memcpy
12890 .{ .tag = @enumFromInt(3859), .properties = .{ .param_str = "v*v*vC*z", .header = .string, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
12891 // memmove
12892 .{ .tag = @enumFromInt(3860), .properties = .{ .param_str = "v*v*vC*z", .header = .string, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
12893 // mempcpy
12894 .{ .tag = @enumFromInt(3861), .properties = .{ .param_str = "v*v*vC*z", .header = .string, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
12895 // memset
12896 .{ .tag = @enumFromInt(3862), .properties = .{ .param_str = "v*v*iz", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
12897 // modf
12898 .{ .tag = @enumFromInt(3863), .properties = .{ .param_str = "ddd*", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12899 // modff
12900 .{ .tag = @enumFromInt(3864), .properties = .{ .param_str = "fff*", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12901 // modfl
12902 .{ .tag = @enumFromInt(3865), .properties = .{ .param_str = "LdLdLd*", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12903 // nan
12904 .{ .tag = @enumFromInt(3866), .properties = .{ .param_str = "dcC*", .header = .math, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12905 // nanf
12906 .{ .tag = @enumFromInt(3867), .properties = .{ .param_str = "fcC*", .header = .math, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12907 // nanl
12908 .{ .tag = @enumFromInt(3868), .properties = .{ .param_str = "LdcC*", .header = .math, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
12909 // nearbyint
12910 .{ .tag = @enumFromInt(3869), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12911 // nearbyintf
12912 .{ .tag = @enumFromInt(3870), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12913 // nearbyintl
12914 .{ .tag = @enumFromInt(3871), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12915 // nextafter
12916 .{ .tag = @enumFromInt(3872), .properties = .{ .param_str = "ddd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12917 // nextafterf
12918 .{ .tag = @enumFromInt(3873), .properties = .{ .param_str = "fff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12919 // nextafterl
12920 .{ .tag = @enumFromInt(3874), .properties = .{ .param_str = "LdLdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12921 // nexttoward
12922 .{ .tag = @enumFromInt(3875), .properties = .{ .param_str = "ddLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12923 // nexttowardf
12924 .{ .tag = @enumFromInt(3876), .properties = .{ .param_str = "ffLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12925 // nexttowardl
12926 .{ .tag = @enumFromInt(3877), .properties = .{ .param_str = "LdLdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12927 // pow
12928 .{ .tag = @enumFromInt(3878), .properties = .{ .param_str = "ddd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12929 // powf
12930 .{ .tag = @enumFromInt(3879), .properties = .{ .param_str = "fff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12931 // powl
12932 .{ .tag = @enumFromInt(3880), .properties = .{ .param_str = "LdLdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12933 // printf
12934 .{ .tag = @enumFromInt(3881), .properties = .{ .param_str = "icC*.", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .printf } } },
12935 // realloc
12936 .{ .tag = @enumFromInt(3882), .properties = .{ .param_str = "v*v*z", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
12937 // remainder
12938 .{ .tag = @enumFromInt(3883), .properties = .{ .param_str = "ddd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12939 // remainderf
12940 .{ .tag = @enumFromInt(3884), .properties = .{ .param_str = "fff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12941 // remainderl
12942 .{ .tag = @enumFromInt(3885), .properties = .{ .param_str = "LdLdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12943 // remquo
12944 .{ .tag = @enumFromInt(3886), .properties = .{ .param_str = "dddi*", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12945 // remquof
12946 .{ .tag = @enumFromInt(3887), .properties = .{ .param_str = "fffi*", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12947 // remquol
12948 .{ .tag = @enumFromInt(3888), .properties = .{ .param_str = "LdLdLdi*", .header = .math, .attributes = .{ .lib_function_without_prefix = true } } },
12949 // rindex
12950 .{ .tag = @enumFromInt(3889), .properties = .{ .param_str = "c*cC*i", .header = .strings, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
12951 // rint
12952 .{ .tag = @enumFromInt(3890), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_fp_exceptions = true } } },
12953 // rintf
12954 .{ .tag = @enumFromInt(3891), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_fp_exceptions = true } } },
12955 // rintl
12956 .{ .tag = @enumFromInt(3892), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_fp_exceptions = true } } },
12957 // round
12958 .{ .tag = @enumFromInt(3893), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12959 // roundeven
12960 .{ .tag = @enumFromInt(3894), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12961 // roundevenf
12962 .{ .tag = @enumFromInt(3895), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12963 // roundevenl
12964 .{ .tag = @enumFromInt(3896), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12965 // roundf
12966 .{ .tag = @enumFromInt(3897), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12967 // roundl
12968 .{ .tag = @enumFromInt(3898), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
12969 // savectx
12970 .{ .tag = @enumFromInt(3899), .properties = .{ .param_str = "iJ", .header = .setjmp, .attributes = .{ .allow_type_mismatch = true, .lib_function_without_prefix = true, .returns_twice = true } } },
12971 // scalbln
12972 .{ .tag = @enumFromInt(3900), .properties = .{ .param_str = "ddLi", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12973 // scalblnf
12974 .{ .tag = @enumFromInt(3901), .properties = .{ .param_str = "ffLi", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12975 // scalblnl
12976 .{ .tag = @enumFromInt(3902), .properties = .{ .param_str = "LdLdLi", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12977 // scalbn
12978 .{ .tag = @enumFromInt(3903), .properties = .{ .param_str = "ddi", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12979 // scalbnf
12980 .{ .tag = @enumFromInt(3904), .properties = .{ .param_str = "ffi", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12981 // scalbnl
12982 .{ .tag = @enumFromInt(3905), .properties = .{ .param_str = "LdLdi", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12983 // scanf
12984 .{ .tag = @enumFromInt(3906), .properties = .{ .param_str = "icC*R.", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .scanf } } },
12985 // setjmp
12986 .{ .tag = @enumFromInt(3907), .properties = .{ .param_str = "iJ", .header = .setjmp, .attributes = .{ .allow_type_mismatch = true, .lib_function_without_prefix = true, .returns_twice = true } } },
12987 // siglongjmp
12988 .{ .tag = @enumFromInt(3908), .properties = .{ .param_str = "vSJi", .header = .setjmp, .language = .all_gnu_languages, .attributes = .{ .noreturn = true, .allow_type_mismatch = true, .lib_function_without_prefix = true } } },
12989 // sigsetjmp
12990 .{ .tag = @enumFromInt(3909), .properties = .{ .param_str = "iSJi", .header = .setjmp, .attributes = .{ .allow_type_mismatch = true, .lib_function_without_prefix = true, .returns_twice = true } } },
12991 // sin
12992 .{ .tag = @enumFromInt(3910), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12993 // sinf
12994 .{ .tag = @enumFromInt(3911), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12995 // sinh
12996 .{ .tag = @enumFromInt(3912), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12997 // sinhf
12998 .{ .tag = @enumFromInt(3913), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
12999 // sinhl
13000 .{ .tag = @enumFromInt(3914), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13001 // sinl
13002 .{ .tag = @enumFromInt(3915), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13003 // snprintf
13004 .{ .tag = @enumFromInt(3916), .properties = .{ .param_str = "ic*zcC*.", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .printf, .format_string_position = 2 } } },
13005 // sprintf
13006 .{ .tag = @enumFromInt(3917), .properties = .{ .param_str = "ic*cC*.", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .printf, .format_string_position = 1 } } },
13007 // sqrt
13008 .{ .tag = @enumFromInt(3918), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13009 // sqrtf
13010 .{ .tag = @enumFromInt(3919), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13011 // sqrtl
13012 .{ .tag = @enumFromInt(3920), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13013 // sscanf
13014 .{ .tag = @enumFromInt(3921), .properties = .{ .param_str = "icC*RcC*R.", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .scanf, .format_string_position = 1 } } },
13015 // stpcpy
13016 .{ .tag = @enumFromInt(3922), .properties = .{ .param_str = "c*c*cC*", .header = .string, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
13017 // stpncpy
13018 .{ .tag = @enumFromInt(3923), .properties = .{ .param_str = "c*c*cC*z", .header = .string, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
13019 // strcasecmp
13020 .{ .tag = @enumFromInt(3924), .properties = .{ .param_str = "icC*cC*", .header = .strings, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
13021 // strcat
13022 .{ .tag = @enumFromInt(3925), .properties = .{ .param_str = "c*c*cC*", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13023 // strchr
13024 .{ .tag = @enumFromInt(3926), .properties = .{ .param_str = "c*cC*i", .header = .string, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13025 // strcmp
13026 .{ .tag = @enumFromInt(3927), .properties = .{ .param_str = "icC*cC*", .header = .string, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13027 // strcpy
13028 .{ .tag = @enumFromInt(3928), .properties = .{ .param_str = "c*c*cC*", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13029 // strcspn
13030 .{ .tag = @enumFromInt(3929), .properties = .{ .param_str = "zcC*cC*", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13031 // strdup
13032 .{ .tag = @enumFromInt(3930), .properties = .{ .param_str = "c*cC*", .header = .string, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
13033 // strerror
13034 .{ .tag = @enumFromInt(3931), .properties = .{ .param_str = "c*i", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13035 // strlcat
13036 .{ .tag = @enumFromInt(3932), .properties = .{ .param_str = "zc*cC*z", .header = .string, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
13037 // strlcpy
13038 .{ .tag = @enumFromInt(3933), .properties = .{ .param_str = "zc*cC*z", .header = .string, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
13039 // strlen
13040 .{ .tag = @enumFromInt(3934), .properties = .{ .param_str = "zcC*", .header = .string, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13041 // strncasecmp
13042 .{ .tag = @enumFromInt(3935), .properties = .{ .param_str = "icC*cC*z", .header = .strings, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
13043 // strncat
13044 .{ .tag = @enumFromInt(3936), .properties = .{ .param_str = "c*c*cC*z", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13045 // strncmp
13046 .{ .tag = @enumFromInt(3937), .properties = .{ .param_str = "icC*cC*z", .header = .string, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13047 // strncpy
13048 .{ .tag = @enumFromInt(3938), .properties = .{ .param_str = "c*c*cC*z", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13049 // strndup
13050 .{ .tag = @enumFromInt(3939), .properties = .{ .param_str = "c*cC*z", .header = .string, .language = .all_gnu_languages, .attributes = .{ .lib_function_without_prefix = true } } },
13051 // strpbrk
13052 .{ .tag = @enumFromInt(3940), .properties = .{ .param_str = "c*cC*cC*", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13053 // strrchr
13054 .{ .tag = @enumFromInt(3941), .properties = .{ .param_str = "c*cC*i", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13055 // strspn
13056 .{ .tag = @enumFromInt(3942), .properties = .{ .param_str = "zcC*cC*", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13057 // strstr
13058 .{ .tag = @enumFromInt(3943), .properties = .{ .param_str = "c*cC*cC*", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13059 // strtod
13060 .{ .tag = @enumFromInt(3944), .properties = .{ .param_str = "dcC*c**", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
13061 // strtof
13062 .{ .tag = @enumFromInt(3945), .properties = .{ .param_str = "fcC*c**", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
13063 // strtok
13064 .{ .tag = @enumFromInt(3946), .properties = .{ .param_str = "c*c*cC*", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13065 // strtol
13066 .{ .tag = @enumFromInt(3947), .properties = .{ .param_str = "LicC*c**i", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
13067 // strtold
13068 .{ .tag = @enumFromInt(3948), .properties = .{ .param_str = "LdcC*c**", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
13069 // strtoll
13070 .{ .tag = @enumFromInt(3949), .properties = .{ .param_str = "LLicC*c**i", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
13071 // strtoul
13072 .{ .tag = @enumFromInt(3950), .properties = .{ .param_str = "ULicC*c**i", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
13073 // strtoull
13074 .{ .tag = @enumFromInt(3951), .properties = .{ .param_str = "ULLicC*c**i", .header = .stdlib, .attributes = .{ .lib_function_without_prefix = true } } },
13075 // strxfrm
13076 .{ .tag = @enumFromInt(3952), .properties = .{ .param_str = "zc*cC*z", .header = .string, .attributes = .{ .lib_function_without_prefix = true } } },
13077 // tan
13078 .{ .tag = @enumFromInt(3953), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13079 // tanf
13080 .{ .tag = @enumFromInt(3954), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13081 // tanh
13082 .{ .tag = @enumFromInt(3955), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13083 // tanhf
13084 .{ .tag = @enumFromInt(3956), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13085 // tanhl
13086 .{ .tag = @enumFromInt(3957), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13087 // tanl
13088 .{ .tag = @enumFromInt(3958), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13089 // tgamma
13090 .{ .tag = @enumFromInt(3959), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13091 // tgammaf
13092 .{ .tag = @enumFromInt(3960), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13093 // tgammal
13094 .{ .tag = @enumFromInt(3961), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .lib_function_without_prefix = true, .const_without_errno_and_fp_exceptions = true } } },
13095 // tolower
13096 .{ .tag = @enumFromInt(3962), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
13097 // toupper
13098 .{ .tag = @enumFromInt(3963), .properties = .{ .param_str = "ii", .header = .ctype, .attributes = .{ .pure = true, .lib_function_without_prefix = true } } },
13099 // trunc
13100 .{ .tag = @enumFromInt(3964), .properties = .{ .param_str = "dd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
13101 // truncf
13102 .{ .tag = @enumFromInt(3965), .properties = .{ .param_str = "ff", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
13103 // truncl
13104 .{ .tag = @enumFromInt(3966), .properties = .{ .param_str = "LdLd", .header = .math, .attributes = .{ .@"const" = true, .lib_function_without_prefix = true } } },
13105 // va_copy
13106 .{ .tag = @enumFromInt(3967), .properties = .{ .param_str = "vAA", .header = .stdarg, .attributes = .{ .lib_function_without_prefix = true } } },
13107 // va_end
13108 .{ .tag = @enumFromInt(3968), .properties = .{ .param_str = "vA", .header = .stdarg, .attributes = .{ .lib_function_without_prefix = true } } },
13109 // va_start
13110 .{ .tag = @enumFromInt(3969), .properties = .{ .param_str = "vA.", .header = .stdarg, .attributes = .{ .lib_function_without_prefix = true } } },
13111 // vfork
13112 .{ .tag = @enumFromInt(3970), .properties = .{ .param_str = "p", .header = .unistd, .attributes = .{ .allow_type_mismatch = true, .lib_function_without_prefix = true, .returns_twice = true } } },
13113 // vfprintf
13114 .{ .tag = @enumFromInt(3971), .properties = .{ .param_str = "iP*cC*a", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .vprintf, .format_string_position = 1 } } },
13115 // vfscanf
13116 .{ .tag = @enumFromInt(3972), .properties = .{ .param_str = "iP*RcC*Ra", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .vscanf, .format_string_position = 1 } } },
13117 // vprintf
13118 .{ .tag = @enumFromInt(3973), .properties = .{ .param_str = "icC*a", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .vprintf } } },
13119 // vscanf
13120 .{ .tag = @enumFromInt(3974), .properties = .{ .param_str = "icC*Ra", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .vscanf } } },
13121 // vsnprintf
13122 .{ .tag = @enumFromInt(3975), .properties = .{ .param_str = "ic*zcC*a", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .vprintf, .format_string_position = 2 } } },
13123 // vsprintf
13124 .{ .tag = @enumFromInt(3976), .properties = .{ .param_str = "ic*cC*a", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .vprintf, .format_string_position = 1 } } },
13125 // vsscanf
13126 .{ .tag = @enumFromInt(3977), .properties = .{ .param_str = "icC*RcC*Ra", .header = .stdio, .attributes = .{ .lib_function_without_prefix = true, .format_kind = .vscanf, .format_string_position = 1 } } },
13127 // wcschr
13128 .{ .tag = @enumFromInt(3978), .properties = .{ .param_str = "w*wC*w", .header = .wchar, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13129 // wcscmp
13130 .{ .tag = @enumFromInt(3979), .properties = .{ .param_str = "iwC*wC*", .header = .wchar, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13131 // wcslen
13132 .{ .tag = @enumFromInt(3980), .properties = .{ .param_str = "zwC*", .header = .wchar, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13133 // wcsncmp
13134 .{ .tag = @enumFromInt(3981), .properties = .{ .param_str = "iwC*wC*z", .header = .wchar, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13135 // wmemchr
13136 .{ .tag = @enumFromInt(3982), .properties = .{ .param_str = "w*wC*wz", .header = .wchar, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13137 // wmemcmp
13138 .{ .tag = @enumFromInt(3983), .properties = .{ .param_str = "iwC*wC*z", .header = .wchar, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13139 // wmemcpy
13140 .{ .tag = @enumFromInt(3984), .properties = .{ .param_str = "w*w*wC*z", .header = .wchar, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13141 // wmemmove
13142 .{ .tag = @enumFromInt(3985), .properties = .{ .param_str = "w*w*wC*z", .header = .wchar, .attributes = .{ .lib_function_without_prefix = true, .const_evaluable = true } } },
13143 };
13144};
13145};
13146}
lib/compiler/aro/aro/Builtins/Properties.zig deleted-143
...@@ -1,143 +0,0 @@
1const std = @import("std");
2
3const Properties = @This();
4
5param_str: []const u8,
6language: Language = .all_languages,
7attributes: Attributes = Attributes{},
8header: Header = .none,
9target_set: TargetSet = TargetSet.initOne(.basic),
10
11/// Header which must be included for a builtin to be available
12pub const Header = enum {
13 none,
14 /// stdio.h
15 stdio,
16 /// stdlib.h
17 stdlib,
18 /// setjmpex.h
19 setjmpex,
20 /// stdarg.h
21 stdarg,
22 /// string.h
23 string,
24 /// ctype.h
25 ctype,
26 /// wchar.h
27 wchar,
28 /// setjmp.h
29 setjmp,
30 /// malloc.h
31 malloc,
32 /// strings.h
33 strings,
34 /// unistd.h
35 unistd,
36 /// pthread.h
37 pthread,
38 /// math.h
39 math,
40 /// complex.h
41 complex,
42 /// Blocks.h
43 blocks,
44};
45
46/// Languages in which a builtin is available
47pub const Language = enum {
48 all_languages,
49 all_ms_languages,
50 all_gnu_languages,
51 gnu_lang,
52};
53
54pub const Attributes = packed struct {
55 /// Function does not return
56 noreturn: bool = false,
57
58 /// Function has no side effects
59 pure: bool = false,
60
61 /// Function has no side effects and does not read memory
62 @"const": bool = false,
63
64 /// Signature is meaningless; use custom typecheck
65 custom_typecheck: bool = false,
66
67 /// A declaration of this builtin should be recognized even if the type doesn't match the specified signature.
68 allow_type_mismatch: bool = false,
69
70 /// this is a libc/libm function with a '__builtin_' prefix added.
71 lib_function_with_builtin_prefix: bool = false,
72
73 /// this is a libc/libm function without a '__builtin_' prefix. This builtin is disableable by '-fno-builtin-foo'
74 lib_function_without_prefix: bool = false,
75
76 /// Function returns twice (e.g. setjmp)
77 returns_twice: bool = false,
78
79 /// Nature of the format string passed to this function
80 format_kind: enum(u3) {
81 /// Does not take a format string
82 none,
83 /// this is a printf-like function whose Nth argument is the format string
84 printf,
85 /// function is like vprintf in that it accepts its arguments as a va_list rather than through an ellipsis
86 vprintf,
87 /// this is a scanf-like function whose Nth argument is the format string
88 scanf,
89 /// the function is like vscanf in that it accepts its arguments as a va_list rather than through an ellipsis
90 vscanf,
91 } = .none,
92
93 /// Position of format string argument. Only meaningful if format_kind is not .none
94 format_string_position: u5 = 0,
95
96 /// if false, arguments are not evaluated
97 eval_args: bool = true,
98
99 /// no side effects and does not read memory, but only when -fno-math-errno and FP exceptions are ignored
100 const_without_errno_and_fp_exceptions: bool = false,
101
102 /// no side effects and does not read memory, but only when FP exceptions are ignored
103 const_without_fp_exceptions: bool = false,
104
105 /// this function can be constant evaluated by the frontend
106 const_evaluable: bool = false,
107};
108
109pub const Target = enum {
110 /// Supported on all targets
111 basic,
112 aarch64,
113 aarch64_neon_sve_bridge,
114 aarch64_neon_sve_bridge_cg,
115 amdgpu,
116 arm,
117 bpf,
118 hexagon,
119 hexagon_dep,
120 hexagon_map_custom_dep,
121 loong_arch,
122 mips,
123 neon,
124 nvptx,
125 ppc,
126 riscv,
127 riscv_vector,
128 sve,
129 systemz,
130 ve,
131 vevl_gen,
132 webassembly,
133 x86,
134 x86_64,
135 xcore,
136};
137
138/// Targets for which a builtin is enabled
139pub const TargetSet = std.enums.EnumSet(Target);
140
141pub fn isVarArgs(properties: Properties) bool {
142 return properties.param_str[properties.param_str.len - 1] == '.';
143}
lib/compiler/aro/aro/Builtins/TypeDescription.zig deleted-286
...@@ -1,286 +0,0 @@
1const std = @import("std");
2
3const TypeDescription = @This();
4
5prefix: []const Prefix,
6spec: Spec,
7suffix: []const Suffix,
8
9pub const Component = union(enum) {
10 prefix: Prefix,
11 spec: Spec,
12 suffix: Suffix,
13};
14
15pub const ComponentIterator = struct {
16 str: []const u8,
17 idx: usize,
18
19 pub fn init(str: []const u8) ComponentIterator {
20 return .{
21 .str = str,
22 .idx = 0,
23 };
24 }
25
26 pub fn peek(self: *ComponentIterator) ?Component {
27 const idx = self.idx;
28 defer self.idx = idx;
29 return self.next();
30 }
31
32 pub fn next(self: *ComponentIterator) ?Component {
33 if (self.idx == self.str.len) return null;
34 const c = self.str[self.idx];
35 self.idx += 1;
36 switch (c) {
37 'L' => {
38 if (self.str[self.idx] != 'L') return .{ .prefix = .L };
39 self.idx += 1;
40 if (self.str[self.idx] != 'L') return .{ .prefix = .LL };
41 self.idx += 1;
42 return .{ .prefix = .LLL };
43 },
44 'Z' => return .{ .prefix = .Z },
45 'W' => return .{ .prefix = .W },
46 'N' => return .{ .prefix = .N },
47 'O' => return .{ .prefix = .O },
48 'S' => {
49 if (self.str[self.idx] == 'J') {
50 self.idx += 1;
51 return .{ .spec = .SJ };
52 }
53 return .{ .prefix = .S };
54 },
55 'U' => return .{ .prefix = .U },
56 'I' => return .{ .prefix = .I },
57
58 'v' => return .{ .spec = .v },
59 'b' => return .{ .spec = .b },
60 'c' => return .{ .spec = .c },
61 's' => return .{ .spec = .s },
62 'i' => return .{ .spec = .i },
63 'h' => return .{ .spec = .h },
64 'x' => return .{ .spec = .x },
65 'y' => return .{ .spec = .y },
66 'f' => return .{ .spec = .f },
67 'd' => return .{ .spec = .d },
68 'z' => return .{ .spec = .z },
69 'w' => return .{ .spec = .w },
70 'F' => return .{ .spec = .F },
71 'G' => return .{ .spec = .G },
72 'H' => return .{ .spec = .H },
73 'M' => return .{ .spec = .M },
74 'a' => return .{ .spec = .a },
75 'A' => return .{ .spec = .A },
76 'V', 'q', 'E' => {
77 const start = self.idx;
78 while (std.ascii.isDigit(self.str[self.idx])) : (self.idx += 1) {}
79 const count = std.fmt.parseUnsigned(u32, self.str[start..self.idx], 10) catch unreachable;
80 return switch (c) {
81 'V' => .{ .spec = .{ .V = count } },
82 'q' => .{ .spec = .{ .q = count } },
83 'E' => .{ .spec = .{ .E = count } },
84 else => unreachable,
85 };
86 },
87 'X' => {
88 defer self.idx += 1;
89 switch (self.str[self.idx]) {
90 'f' => return .{ .spec = .{ .X = .float } },
91 'd' => return .{ .spec = .{ .X = .double } },
92 'L' => {
93 self.idx += 1;
94 return .{ .spec = .{ .X = .longdouble } };
95 },
96 else => unreachable,
97 }
98 },
99 'Y' => return .{ .spec = .Y },
100 'P' => return .{ .spec = .P },
101 'J' => return .{ .spec = .J },
102 'K' => return .{ .spec = .K },
103 'p' => return .{ .spec = .p },
104 '.' => {
105 // can only appear at end of param string; indicates varargs function
106 std.debug.assert(self.idx == self.str.len);
107 return null;
108 },
109 '!' => {
110 std.debug.assert(self.str.len == 1);
111 return .{ .spec = .@"!" };
112 },
113
114 '*' => {
115 if (self.idx < self.str.len and std.ascii.isDigit(self.str[self.idx])) {
116 defer self.idx += 1;
117 const addr_space = self.str[self.idx] - '0';
118 return .{ .suffix = .{ .@"*" = addr_space } };
119 } else {
120 return .{ .suffix = .{ .@"*" = null } };
121 }
122 },
123 'C' => return .{ .suffix = .C },
124 'D' => return .{ .suffix = .D },
125 'R' => return .{ .suffix = .R },
126 else => unreachable,
127 }
128 return null;
129 }
130};
131
132pub const TypeIterator = struct {
133 param_str: []const u8,
134 prefix: [4]Prefix,
135 spec: Spec,
136 suffix: [4]Suffix,
137 idx: usize,
138
139 pub fn init(param_str: []const u8) TypeIterator {
140 return .{
141 .param_str = param_str,
142 .prefix = undefined,
143 .spec = undefined,
144 .suffix = undefined,
145 .idx = 0,
146 };
147 }
148
149 /// Returned `TypeDescription` contains fields which are slices into the underlying `TypeIterator`
150 /// The returned value is invalidated when `.next()` is called again or the TypeIterator goes out
151 // of scope.
152 pub fn next(self: *TypeIterator) ?TypeDescription {
153 var it = ComponentIterator.init(self.param_str[self.idx..]);
154 defer self.idx += it.idx;
155
156 var prefix_count: usize = 0;
157 var maybe_spec: ?Spec = null;
158 var suffix_count: usize = 0;
159 while (it.peek()) |component| {
160 switch (component) {
161 .prefix => |prefix| {
162 if (maybe_spec != null) break;
163 self.prefix[prefix_count] = prefix;
164 prefix_count += 1;
165 },
166 .spec => |spec| {
167 if (maybe_spec != null) break;
168 maybe_spec = spec;
169 },
170 .suffix => |suffix| {
171 std.debug.assert(maybe_spec != null);
172 self.suffix[suffix_count] = suffix;
173 suffix_count += 1;
174 },
175 }
176 _ = it.next();
177 }
178 if (maybe_spec) |spec| {
179 return TypeDescription{
180 .prefix = self.prefix[0..prefix_count],
181 .spec = spec,
182 .suffix = self.suffix[0..suffix_count],
183 };
184 }
185 return null;
186 }
187};
188
189const Prefix = enum {
190 /// long (e.g. Li for 'long int', Ld for 'long double')
191 L,
192 /// long long (e.g. LLi for 'long long int', LLd for __float128)
193 LL,
194 /// __int128_t (e.g. LLLi)
195 LLL,
196 /// int32_t (require a native 32-bit integer type on the target)
197 Z,
198 /// int64_t (require a native 64-bit integer type on the target)
199 W,
200 /// 'int' size if target is LP64, 'L' otherwise.
201 N,
202 /// long for OpenCL targets, long long otherwise.
203 O,
204 /// signed
205 S,
206 /// unsigned
207 U,
208 /// Required to constant fold to an integer constant expression.
209 I,
210};
211
212const Spec = union(enum) {
213 /// void
214 v,
215 /// boolean
216 b,
217 /// char
218 c,
219 /// short
220 s,
221 /// int
222 i,
223 /// half (__fp16, OpenCL)
224 h,
225 /// half (_Float16)
226 x,
227 /// half (__bf16)
228 y,
229 /// float
230 f,
231 /// double
232 d,
233 /// size_t
234 z,
235 /// wchar_t
236 w,
237 /// constant CFString
238 F,
239 /// id
240 G,
241 /// SEL
242 H,
243 /// struct objc_super
244 M,
245 /// __builtin_va_list
246 a,
247 /// "reference" to __builtin_va_list
248 A,
249 /// Vector, followed by the number of elements and the base type.
250 V: u32,
251 /// Scalable vector, followed by the number of elements and the base type.
252 q: u32,
253 /// ext_vector, followed by the number of elements and the base type.
254 E: u32,
255 /// _Complex, followed by the base type.
256 X: enum {
257 float,
258 double,
259 longdouble,
260 },
261 /// ptrdiff_t
262 Y,
263 /// FILE
264 P,
265 /// jmp_buf
266 J,
267 /// sigjmp_buf
268 SJ,
269 /// ucontext_t
270 K,
271 /// pid_t
272 p,
273 /// Used to indicate a builtin with target-dependent param types. Must appear by itself
274 @"!",
275};
276
277const Suffix = union(enum) {
278 /// pointer (optionally followed by an address space number,if no address space is specified than any address space will be accepted)
279 @"*": ?u8,
280 /// const
281 C,
282 /// volatile
283 D,
284 /// restrict
285 R,
286};
lib/compiler/aro/aro/Builtins/eval.zig deleted-86
...@@ -1,86 +0,0 @@
1const std = @import("std");
2const backend = @import("../../backend.zig");
3const Interner = backend.Interner;
4const Builtins = @import("../Builtins.zig");
5const Builtin = Builtins.Builtin;
6const Parser = @import("../Parser.zig");
7const Tree = @import("../Tree.zig");
8const NodeIndex = Tree.NodeIndex;
9const Type = @import("../Type.zig");
10const Value = @import("../Value.zig");
11
12fn makeNan(comptime T: type, str: []const u8) T {
13 const UnsignedSameSize = std.meta.Int(.unsigned, @bitSizeOf(T));
14 const parsed = std.fmt.parseUnsigned(UnsignedSameSize, str[0 .. str.len - 1], 0) catch 0;
15 const bits: switch (T) {
16 f32 => u23,
17 f64 => u52,
18 f80 => u63,
19 f128 => u112,
20 else => @compileError("Invalid type for makeNan"),
21 } = @truncate(parsed);
22 return @bitCast(@as(UnsignedSameSize, bits) | @as(UnsignedSameSize, @bitCast(std.math.nan(T))));
23}
24
25pub fn eval(tag: Builtin.Tag, p: *Parser, args: []const NodeIndex) !Value {
26 const builtin = Builtin.fromTag(tag);
27 if (!builtin.properties.attributes.const_evaluable) return .{};
28
29 switch (tag) {
30 Builtin.tagFromName("__builtin_inff").?,
31 Builtin.tagFromName("__builtin_inf").?,
32 Builtin.tagFromName("__builtin_infl").?,
33 => {
34 const ty: Type = switch (tag) {
35 Builtin.tagFromName("__builtin_inff").? => .{ .specifier = .float },
36 Builtin.tagFromName("__builtin_inf").? => .{ .specifier = .double },
37 Builtin.tagFromName("__builtin_infl").? => .{ .specifier = .long_double },
38 else => unreachable,
39 };
40 const f: Interner.Key.Float = switch (ty.bitSizeof(p.comp).?) {
41 32 => .{ .f32 = std.math.inf(f32) },
42 64 => .{ .f64 = std.math.inf(f64) },
43 80 => .{ .f80 = std.math.inf(f80) },
44 128 => .{ .f128 = std.math.inf(f128) },
45 else => unreachable,
46 };
47 return Value.intern(p.comp, .{ .float = f });
48 },
49 Builtin.tagFromName("__builtin_isinf").? => blk: {
50 if (args.len == 0) break :blk;
51 const val = p.value_map.get(args[0]) orelse break :blk;
52 return Value.fromBool(val.isInf(p.comp));
53 },
54 Builtin.tagFromName("__builtin_isinf_sign").? => blk: {
55 if (args.len == 0) break :blk;
56 const val = p.value_map.get(args[0]) orelse break :blk;
57 switch (val.isInfSign(p.comp)) {
58 .unknown => {},
59 .finite => return Value.zero,
60 .positive => return Value.one,
61 .negative => return Value.int(@as(i64, -1), p.comp),
62 }
63 },
64 Builtin.tagFromName("__builtin_isnan").? => blk: {
65 if (args.len == 0) break :blk;
66 const val = p.value_map.get(args[0]) orelse break :blk;
67 return Value.fromBool(val.isNan(p.comp));
68 },
69 Builtin.tagFromName("__builtin_nan").? => blk: {
70 if (args.len == 0) break :blk;
71 const val = p.getDecayedStringLiteral(args[0]) orelse break :blk;
72 const bytes = p.comp.interner.get(val.ref()).bytes;
73
74 const f: Interner.Key.Float = switch ((Type{ .specifier = .double }).bitSizeof(p.comp).?) {
75 32 => .{ .f32 = makeNan(f32, bytes) },
76 64 => .{ .f64 = makeNan(f64, bytes) },
77 80 => .{ .f80 = makeNan(f80, bytes) },
78 128 => .{ .f128 = makeNan(f128, bytes) },
79 else => unreachable,
80 };
81 return Value.intern(p.comp, .{ .float = f });
82 },
83 else => {},
84 }
85 return .{};
86}
lib/compiler/aro/aro/CodeGen.zig deleted-1295
...@@ -1,1295 +0,0 @@
1const std = @import("std");
2const Allocator = std.mem.Allocator;
3const assert = std.debug.assert;
4const backend = @import("../backend.zig");
5const Interner = backend.Interner;
6const Ir = backend.Ir;
7const Builtins = @import("Builtins.zig");
8const Builtin = Builtins.Builtin;
9const Compilation = @import("Compilation.zig");
10const Builder = Ir.Builder;
11const StrInt = @import("StringInterner.zig");
12const StringId = StrInt.StringId;
13const Tree = @import("Tree.zig");
14const NodeIndex = Tree.NodeIndex;
15const Type = @import("Type.zig");
16const Value = @import("Value.zig");
17
18const WipSwitch = struct {
19 cases: Cases = .{},
20 default: ?Ir.Ref = null,
21 size: u64,
22
23 const Cases = std.MultiArrayList(struct {
24 val: Interner.Ref,
25 label: Ir.Ref,
26 });
27};
28
29const Symbol = struct {
30 name: StringId,
31 val: Ir.Ref,
32};
33
34const Error = Compilation.Error;
35
36const CodeGen = @This();
37
38tree: Tree,
39comp: *Compilation,
40builder: Builder,
41node_tag: []const Tree.Tag,
42node_data: []const Tree.Node.Data,
43node_ty: []const Type,
44wip_switch: *WipSwitch = undefined,
45symbols: std.ArrayListUnmanaged(Symbol) = .empty,
46ret_nodes: std.ArrayListUnmanaged(Ir.Inst.Phi.Input) = .empty,
47phi_nodes: std.ArrayListUnmanaged(Ir.Inst.Phi.Input) = .empty,
48record_elem_buf: std.ArrayListUnmanaged(Interner.Ref) = .empty,
49record_cache: std.AutoHashMapUnmanaged(*Type.Record, Interner.Ref) = .empty,
50cond_dummy_ty: ?Interner.Ref = null,
51bool_invert: bool = false,
52bool_end_label: Ir.Ref = .none,
53cond_dummy_ref: Ir.Ref = undefined,
54continue_label: Ir.Ref = undefined,
55break_label: Ir.Ref = undefined,
56return_label: Ir.Ref = undefined,
57
58fn fail(c: *CodeGen, comptime fmt: []const u8, args: anytype) error{ FatalError, OutOfMemory } {
59 try c.comp.diagnostics.list.append(c.comp.gpa, .{
60 .tag = .cli_error,
61 .kind = .@"fatal error",
62 .extra = .{ .str = try std.fmt.allocPrint(c.comp.diagnostics.arena.allocator(), fmt, args) },
63 });
64 return error.FatalError;
65}
66
67pub fn genIr(tree: Tree) Compilation.Error!Ir {
68 const gpa = tree.comp.gpa;
69 var c = CodeGen{
70 .builder = .{
71 .gpa = tree.comp.gpa,
72 .interner = &tree.comp.interner,
73 .arena = std.heap.ArenaAllocator.init(gpa),
74 },
75 .tree = tree,
76 .comp = tree.comp,
77 .node_tag = tree.nodes.items(.tag),
78 .node_data = tree.nodes.items(.data),
79 .node_ty = tree.nodes.items(.ty),
80 };
81 defer c.symbols.deinit(gpa);
82 defer c.ret_nodes.deinit(gpa);
83 defer c.phi_nodes.deinit(gpa);
84 defer c.record_elem_buf.deinit(gpa);
85 defer c.record_cache.deinit(gpa);
86 defer c.builder.deinit();
87
88 const node_tags = tree.nodes.items(.tag);
89 for (tree.root_decls) |decl| {
90 c.builder.arena.deinit();
91 c.builder.arena = std.heap.ArenaAllocator.init(gpa);
92
93 switch (node_tags[@intFromEnum(decl)]) {
94 .static_assert,
95 .typedef,
96 .struct_decl_two,
97 .union_decl_two,
98 .enum_decl_two,
99 .struct_decl,
100 .union_decl,
101 .enum_decl,
102 => {},
103
104 .fn_proto,
105 .static_fn_proto,
106 .inline_fn_proto,
107 .inline_static_fn_proto,
108 .extern_var,
109 .threadlocal_extern_var,
110 => {},
111
112 .fn_def,
113 .static_fn_def,
114 .inline_fn_def,
115 .inline_static_fn_def,
116 => c.genFn(decl) catch |err| switch (err) {
117 error.FatalError => return error.FatalError,
118 error.OutOfMemory => return error.OutOfMemory,
119 },
120
121 .@"var",
122 .static_var,
123 .threadlocal_var,
124 .threadlocal_static_var,
125 => c.genVar(decl) catch |err| switch (err) {
126 error.FatalError => return error.FatalError,
127 error.OutOfMemory => return error.OutOfMemory,
128 },
129 else => unreachable,
130 }
131 }
132 return c.builder.finish();
133}
134
135fn genType(c: *CodeGen, base_ty: Type) !Interner.Ref {
136 var key: Interner.Key = undefined;
137 const ty = base_ty.canonicalize(.standard);
138 switch (ty.specifier) {
139 .void => return .void,
140 .bool => return .i1,
141 .@"struct" => {
142 if (c.record_cache.get(ty.data.record)) |some| return some;
143
144 const elem_buf_top = c.record_elem_buf.items.len;
145 defer c.record_elem_buf.items.len = elem_buf_top;
146
147 for (ty.data.record.fields) |field| {
148 if (!field.isRegularField()) {
149 return c.fail("TODO lower struct bitfields", .{});
150 }
151 // TODO handle padding bits
152 const field_ref = try c.genType(field.ty);
153 try c.record_elem_buf.append(c.builder.gpa, field_ref);
154 }
155
156 return c.builder.interner.put(c.builder.gpa, .{
157 .record_ty = c.record_elem_buf.items[elem_buf_top..],
158 });
159 },
160 .@"union" => {
161 return c.fail("TODO lower union types", .{});
162 },
163 else => {},
164 }
165 if (ty.isPtr()) return .ptr;
166 if (ty.isFunc()) return .func;
167 if (!ty.isReal()) return c.fail("TODO lower complex types", .{});
168 if (ty.isInt()) {
169 const bits = ty.bitSizeof(c.comp).?;
170 key = .{ .int_ty = @intCast(bits) };
171 } else if (ty.isFloat()) {
172 const bits = ty.bitSizeof(c.comp).?;
173 key = .{ .float_ty = @intCast(bits) };
174 } else if (ty.isArray()) {
175 const elem = try c.genType(ty.elemType());
176 key = .{ .array_ty = .{ .child = elem, .len = ty.arrayLen().? } };
177 } else if (ty.specifier == .vector) {
178 const elem = try c.genType(ty.elemType());
179 key = .{ .vector_ty = .{ .child = elem, .len = @intCast(ty.data.array.len) } };
180 } else if (ty.is(.nullptr_t)) {
181 return c.fail("TODO lower nullptr_t", .{});
182 }
183 return c.builder.interner.put(c.builder.gpa, key);
184}
185
186fn genFn(c: *CodeGen, decl: NodeIndex) Error!void {
187 const name = c.tree.tokSlice(c.node_data[@intFromEnum(decl)].decl.name);
188 const func_ty = c.node_ty[@intFromEnum(decl)].canonicalize(.standard);
189 c.ret_nodes.items.len = 0;
190
191 try c.builder.startFn();
192
193 for (func_ty.data.func.params) |param| {
194 // TODO handle calling convention here
195 const arg = try c.builder.addArg(try c.genType(param.ty));
196
197 const size: u32 = @intCast(param.ty.sizeof(c.comp).?); // TODO add error in parser
198 const @"align" = param.ty.alignof(c.comp);
199 const alloc = try c.builder.addAlloc(size, @"align");
200 try c.builder.addStore(alloc, arg);
201 try c.symbols.append(c.comp.gpa, .{ .name = param.name, .val = alloc });
202 }
203
204 // Generate body
205 c.return_label = try c.builder.makeLabel("return");
206 try c.genStmt(c.node_data[@intFromEnum(decl)].decl.node);
207
208 // Relocate returns
209 if (c.ret_nodes.items.len == 0) {
210 _ = try c.builder.addInst(.ret, .{ .un = .none }, .noreturn);
211 } else if (c.ret_nodes.items.len == 1) {
212 c.builder.body.items.len -= 1;
213 _ = try c.builder.addInst(.ret, .{ .un = c.ret_nodes.items[0].value }, .noreturn);
214 } else {
215 try c.builder.startBlock(c.return_label);
216 const phi = try c.builder.addPhi(c.ret_nodes.items, try c.genType(func_ty.returnType()));
217 _ = try c.builder.addInst(.ret, .{ .un = phi }, .noreturn);
218 }
219
220 try c.builder.finishFn(name);
221}
222
223fn addUn(c: *CodeGen, tag: Ir.Inst.Tag, operand: Ir.Ref, ty: Type) !Ir.Ref {
224 return c.builder.addInst(tag, .{ .un = operand }, try c.genType(ty));
225}
226
227fn addBin(c: *CodeGen, tag: Ir.Inst.Tag, lhs: Ir.Ref, rhs: Ir.Ref, ty: Type) !Ir.Ref {
228 return c.builder.addInst(tag, .{ .bin = .{ .lhs = lhs, .rhs = rhs } }, try c.genType(ty));
229}
230
231fn addBranch(c: *CodeGen, cond: Ir.Ref, true_label: Ir.Ref, false_label: Ir.Ref) !void {
232 if (true_label == c.bool_end_label) {
233 if (false_label == c.bool_end_label) {
234 try c.phi_nodes.append(c.comp.gpa, .{ .label = c.builder.current_label, .value = cond });
235 return;
236 }
237 try c.addBoolPhi(!c.bool_invert);
238 }
239 if (false_label == c.bool_end_label) {
240 try c.addBoolPhi(c.bool_invert);
241 }
242 return c.builder.addBranch(cond, true_label, false_label);
243}
244
245fn addBoolPhi(c: *CodeGen, value: bool) !void {
246 const val = try c.builder.addConstant((try Value.int(@intFromBool(value), c.comp)).ref(), .i1);
247 try c.phi_nodes.append(c.comp.gpa, .{ .label = c.builder.current_label, .value = val });
248}
249
250fn genStmt(c: *CodeGen, node: NodeIndex) Error!void {
251 _ = try c.genExpr(node);
252}
253
254fn genExpr(c: *CodeGen, node: NodeIndex) Error!Ir.Ref {
255 std.debug.assert(node != .none);
256 const ty = c.node_ty[@intFromEnum(node)];
257 if (c.tree.value_map.get(node)) |val| {
258 return c.builder.addConstant(val.ref(), try c.genType(ty));
259 }
260 const data = c.node_data[@intFromEnum(node)];
261 switch (c.node_tag[@intFromEnum(node)]) {
262 .enumeration_ref,
263 .bool_literal,
264 .int_literal,
265 .char_literal,
266 .float_literal,
267 .imaginary_literal,
268 .string_literal_expr,
269 .alignof_expr,
270 => unreachable, // These should have an entry in value_map.
271 .fn_def,
272 .static_fn_def,
273 .inline_fn_def,
274 .inline_static_fn_def,
275 .invalid,
276 .threadlocal_var,
277 => unreachable,
278 .static_assert,
279 .fn_proto,
280 .static_fn_proto,
281 .inline_fn_proto,
282 .inline_static_fn_proto,
283 .extern_var,
284 .threadlocal_extern_var,
285 .typedef,
286 .struct_decl_two,
287 .union_decl_two,
288 .enum_decl_two,
289 .struct_decl,
290 .union_decl,
291 .enum_decl,
292 .enum_field_decl,
293 .record_field_decl,
294 .indirect_record_field_decl,
295 .struct_forward_decl,
296 .union_forward_decl,
297 .enum_forward_decl,
298 .null_stmt,
299 => {},
300 .static_var,
301 .implicit_static_var,
302 .threadlocal_static_var,
303 => try c.genVar(node), // TODO
304 .@"var" => {
305 const size: u32 = @intCast(ty.sizeof(c.comp).?); // TODO add error in parser
306 const @"align" = ty.alignof(c.comp);
307 const alloc = try c.builder.addAlloc(size, @"align");
308 const name = try StrInt.intern(c.comp, c.tree.tokSlice(data.decl.name));
309 try c.symbols.append(c.comp.gpa, .{ .name = name, .val = alloc });
310 if (data.decl.node != .none) {
311 try c.genInitializer(alloc, ty, data.decl.node);
312 }
313 },
314 .labeled_stmt => {
315 const label = try c.builder.makeLabel("label");
316 try c.builder.startBlock(label);
317 try c.genStmt(data.decl.node);
318 },
319 .compound_stmt_two => {
320 const old_sym_len = c.symbols.items.len;
321 c.symbols.items.len = old_sym_len;
322
323 if (data.bin.lhs != .none) try c.genStmt(data.bin.lhs);
324 if (data.bin.rhs != .none) try c.genStmt(data.bin.rhs);
325 },
326 .compound_stmt => {
327 const old_sym_len = c.symbols.items.len;
328 c.symbols.items.len = old_sym_len;
329
330 for (c.tree.data[data.range.start..data.range.end]) |stmt| try c.genStmt(stmt);
331 },
332 .if_then_else_stmt => {
333 const then_label = try c.builder.makeLabel("if.then");
334 const else_label = try c.builder.makeLabel("if.else");
335 const end_label = try c.builder.makeLabel("if.end");
336
337 try c.genBoolExpr(data.if3.cond, then_label, else_label);
338
339 try c.builder.startBlock(then_label);
340 try c.genStmt(c.tree.data[data.if3.body]); // then
341 try c.builder.addJump(end_label);
342
343 try c.builder.startBlock(else_label);
344 try c.genStmt(c.tree.data[data.if3.body + 1]); // else
345
346 try c.builder.startBlock(end_label);
347 },
348 .if_then_stmt => {
349 const then_label = try c.builder.makeLabel("if.then");
350 const end_label = try c.builder.makeLabel("if.end");
351
352 try c.genBoolExpr(data.bin.lhs, then_label, end_label);
353
354 try c.builder.startBlock(then_label);
355 try c.genStmt(data.bin.rhs); // then
356 try c.builder.startBlock(end_label);
357 },
358 .switch_stmt => {
359 var wip_switch = WipSwitch{
360 .size = c.node_ty[@intFromEnum(data.bin.lhs)].sizeof(c.comp).?,
361 };
362 defer wip_switch.cases.deinit(c.builder.gpa);
363
364 const old_wip_switch = c.wip_switch;
365 defer c.wip_switch = old_wip_switch;
366 c.wip_switch = &wip_switch;
367
368 const old_break_label = c.break_label;
369 defer c.break_label = old_break_label;
370 const end_ref = try c.builder.makeLabel("switch.end");
371 c.break_label = end_ref;
372
373 const cond = try c.genExpr(data.bin.lhs);
374 const switch_index = c.builder.instructions.len;
375 _ = try c.builder.addInst(.@"switch", undefined, .noreturn);
376
377 try c.genStmt(data.bin.rhs); // body
378
379 const default_ref = wip_switch.default orelse end_ref;
380 try c.builder.startBlock(end_ref);
381
382 const a = c.builder.arena.allocator();
383 const switch_data = try a.create(Ir.Inst.Switch);
384 switch_data.* = .{
385 .target = cond,
386 .cases_len = @intCast(wip_switch.cases.len),
387 .case_vals = (try a.dupe(Interner.Ref, wip_switch.cases.items(.val))).ptr,
388 .case_labels = (try a.dupe(Ir.Ref, wip_switch.cases.items(.label))).ptr,
389 .default = default_ref,
390 };
391 c.builder.instructions.items(.data)[switch_index] = .{ .@"switch" = switch_data };
392 },
393 .case_stmt => {
394 const val = c.tree.value_map.get(data.bin.lhs).?;
395 const label = try c.builder.makeLabel("case");
396 try c.builder.startBlock(label);
397 try c.wip_switch.cases.append(c.builder.gpa, .{
398 .val = val.ref(),
399 .label = label,
400 });
401 try c.genStmt(data.bin.rhs);
402 },
403 .default_stmt => {
404 const default = try c.builder.makeLabel("default");
405 try c.builder.startBlock(default);
406 c.wip_switch.default = default;
407 try c.genStmt(data.un);
408 },
409 .while_stmt => {
410 const old_break_label = c.break_label;
411 defer c.break_label = old_break_label;
412
413 const old_continue_label = c.continue_label;
414 defer c.continue_label = old_continue_label;
415
416 const cond_label = try c.builder.makeLabel("while.cond");
417 const then_label = try c.builder.makeLabel("while.then");
418 const end_label = try c.builder.makeLabel("while.end");
419
420 c.continue_label = cond_label;
421 c.break_label = end_label;
422
423 try c.builder.startBlock(cond_label);
424 try c.genBoolExpr(data.bin.lhs, then_label, end_label);
425
426 try c.builder.startBlock(then_label);
427 try c.genStmt(data.bin.rhs);
428 try c.builder.addJump(cond_label);
429 try c.builder.startBlock(end_label);
430 },
431 .do_while_stmt => {
432 const old_break_label = c.break_label;
433 defer c.break_label = old_break_label;
434
435 const old_continue_label = c.continue_label;
436 defer c.continue_label = old_continue_label;
437
438 const then_label = try c.builder.makeLabel("do.then");
439 const cond_label = try c.builder.makeLabel("do.cond");
440 const end_label = try c.builder.makeLabel("do.end");
441
442 c.continue_label = cond_label;
443 c.break_label = end_label;
444
445 try c.builder.startBlock(then_label);
446 try c.genStmt(data.bin.rhs);
447
448 try c.builder.startBlock(cond_label);
449 try c.genBoolExpr(data.bin.lhs, then_label, end_label);
450
451 try c.builder.startBlock(end_label);
452 },
453 .for_decl_stmt => {
454 const old_break_label = c.break_label;
455 defer c.break_label = old_break_label;
456
457 const old_continue_label = c.continue_label;
458 defer c.continue_label = old_continue_label;
459
460 const for_decl = data.forDecl(&c.tree);
461 for (for_decl.decls) |decl| try c.genStmt(decl);
462
463 const then_label = try c.builder.makeLabel("for.then");
464 var cond_label = then_label;
465 const cont_label = try c.builder.makeLabel("for.cont");
466 const end_label = try c.builder.makeLabel("for.end");
467
468 c.continue_label = cont_label;
469 c.break_label = end_label;
470
471 if (for_decl.cond != .none) {
472 cond_label = try c.builder.makeLabel("for.cond");
473 try c.builder.startBlock(cond_label);
474 try c.genBoolExpr(for_decl.cond, then_label, end_label);
475 }
476 try c.builder.startBlock(then_label);
477 try c.genStmt(for_decl.body);
478 if (for_decl.incr != .none) {
479 _ = try c.genExpr(for_decl.incr);
480 }
481 try c.builder.addJump(cond_label);
482 try c.builder.startBlock(end_label);
483 },
484 .forever_stmt => {
485 const old_break_label = c.break_label;
486 defer c.break_label = old_break_label;
487
488 const old_continue_label = c.continue_label;
489 defer c.continue_label = old_continue_label;
490
491 const then_label = try c.builder.makeLabel("for.then");
492 const end_label = try c.builder.makeLabel("for.end");
493
494 c.continue_label = then_label;
495 c.break_label = end_label;
496
497 try c.builder.startBlock(then_label);
498 try c.genStmt(data.un);
499 try c.builder.startBlock(end_label);
500 },
501 .for_stmt => {
502 const old_break_label = c.break_label;
503 defer c.break_label = old_break_label;
504
505 const old_continue_label = c.continue_label;
506 defer c.continue_label = old_continue_label;
507
508 const for_stmt = data.forStmt(&c.tree);
509 if (for_stmt.init != .none) _ = try c.genExpr(for_stmt.init);
510
511 const then_label = try c.builder.makeLabel("for.then");
512 var cond_label = then_label;
513 const cont_label = try c.builder.makeLabel("for.cont");
514 const end_label = try c.builder.makeLabel("for.end");
515
516 c.continue_label = cont_label;
517 c.break_label = end_label;
518
519 if (for_stmt.cond != .none) {
520 cond_label = try c.builder.makeLabel("for.cond");
521 try c.builder.startBlock(cond_label);
522 try c.genBoolExpr(for_stmt.cond, then_label, end_label);
523 }
524 try c.builder.startBlock(then_label);
525 try c.genStmt(for_stmt.body);
526 if (for_stmt.incr != .none) {
527 _ = try c.genExpr(for_stmt.incr);
528 }
529 try c.builder.addJump(cond_label);
530 try c.builder.startBlock(end_label);
531 },
532 .continue_stmt => try c.builder.addJump(c.continue_label),
533 .break_stmt => try c.builder.addJump(c.break_label),
534 .return_stmt => {
535 if (data.un != .none) {
536 const operand = try c.genExpr(data.un);
537 try c.ret_nodes.append(c.comp.gpa, .{ .value = operand, .label = c.builder.current_label });
538 }
539 try c.builder.addJump(c.return_label);
540 },
541 .implicit_return => {
542 if (data.return_zero) {
543 const operand = try c.builder.addConstant(.zero, try c.genType(ty));
544 try c.ret_nodes.append(c.comp.gpa, .{ .value = operand, .label = c.builder.current_label });
545 }
546 // No need to emit a jump since implicit_return is always the last instruction.
547 },
548 .case_range_stmt,
549 .goto_stmt,
550 .computed_goto_stmt,
551 .nullptr_literal,
552 => return c.fail("TODO CodeGen.genStmt {}\n", .{c.node_tag[@intFromEnum(node)]}),
553 .comma_expr => {
554 _ = try c.genExpr(data.bin.lhs);
555 return c.genExpr(data.bin.rhs);
556 },
557 .assign_expr => {
558 const rhs = try c.genExpr(data.bin.rhs);
559 const lhs = try c.genLval(data.bin.lhs);
560 try c.builder.addStore(lhs, rhs);
561 return rhs;
562 },
563 .mul_assign_expr => return c.genCompoundAssign(node, .mul),
564 .div_assign_expr => return c.genCompoundAssign(node, .div),
565 .mod_assign_expr => return c.genCompoundAssign(node, .mod),
566 .add_assign_expr => return c.genCompoundAssign(node, .add),
567 .sub_assign_expr => return c.genCompoundAssign(node, .sub),
568 .shl_assign_expr => return c.genCompoundAssign(node, .bit_shl),
569 .shr_assign_expr => return c.genCompoundAssign(node, .bit_shr),
570 .bit_and_assign_expr => return c.genCompoundAssign(node, .bit_and),
571 .bit_xor_assign_expr => return c.genCompoundAssign(node, .bit_xor),
572 .bit_or_assign_expr => return c.genCompoundAssign(node, .bit_or),
573 .bit_or_expr => return c.genBinOp(node, .bit_or),
574 .bit_xor_expr => return c.genBinOp(node, .bit_xor),
575 .bit_and_expr => return c.genBinOp(node, .bit_and),
576 .equal_expr => {
577 const cmp = try c.genComparison(node, .cmp_eq);
578 return c.addUn(.zext, cmp, ty);
579 },
580 .not_equal_expr => {
581 const cmp = try c.genComparison(node, .cmp_ne);
582 return c.addUn(.zext, cmp, ty);
583 },
584 .less_than_expr => {
585 const cmp = try c.genComparison(node, .cmp_lt);
586 return c.addUn(.zext, cmp, ty);
587 },
588 .less_than_equal_expr => {
589 const cmp = try c.genComparison(node, .cmp_lte);
590 return c.addUn(.zext, cmp, ty);
591 },
592 .greater_than_expr => {
593 const cmp = try c.genComparison(node, .cmp_gt);
594 return c.addUn(.zext, cmp, ty);
595 },
596 .greater_than_equal_expr => {
597 const cmp = try c.genComparison(node, .cmp_gte);
598 return c.addUn(.zext, cmp, ty);
599 },
600 .shl_expr => return c.genBinOp(node, .bit_shl),
601 .shr_expr => return c.genBinOp(node, .bit_shr),
602 .add_expr => {
603 if (ty.isPtr()) {
604 const lhs_ty = c.node_ty[@intFromEnum(data.bin.lhs)];
605 if (lhs_ty.isPtr()) {
606 const ptr = try c.genExpr(data.bin.lhs);
607 const offset = try c.genExpr(data.bin.rhs);
608 const offset_ty = c.node_ty[@intFromEnum(data.bin.rhs)];
609 return c.genPtrArithmetic(ptr, offset, offset_ty, ty);
610 } else {
611 const offset = try c.genExpr(data.bin.lhs);
612 const ptr = try c.genExpr(data.bin.rhs);
613 const offset_ty = lhs_ty;
614 return c.genPtrArithmetic(ptr, offset, offset_ty, ty);
615 }
616 }
617 return c.genBinOp(node, .add);
618 },
619 .sub_expr => {
620 if (ty.isPtr()) {
621 const ptr = try c.genExpr(data.bin.lhs);
622 const offset = try c.genExpr(data.bin.rhs);
623 const offset_ty = c.node_ty[@intFromEnum(data.bin.rhs)];
624 return c.genPtrArithmetic(ptr, offset, offset_ty, ty);
625 }
626 return c.genBinOp(node, .sub);
627 },
628 .mul_expr => return c.genBinOp(node, .mul),
629 .div_expr => return c.genBinOp(node, .div),
630 .mod_expr => return c.genBinOp(node, .mod),
631 .addr_of_expr => return try c.genLval(data.un),
632 .deref_expr => {
633 const un_data = c.node_data[@intFromEnum(data.un)];
634 if (c.node_tag[@intFromEnum(data.un)] == .implicit_cast and un_data.cast.kind == .function_to_pointer) {
635 return c.genExpr(data.un);
636 }
637 const operand = try c.genLval(data.un);
638 return c.addUn(.load, operand, ty);
639 },
640 .plus_expr => return c.genExpr(data.un),
641 .negate_expr => {
642 const zero = try c.builder.addConstant(.zero, try c.genType(ty));
643 const operand = try c.genExpr(data.un);
644 return c.addBin(.sub, zero, operand, ty);
645 },
646 .bit_not_expr => {
647 const operand = try c.genExpr(data.un);
648 return c.addUn(.bit_not, operand, ty);
649 },
650 .bool_not_expr => {
651 const zero = try c.builder.addConstant(.zero, try c.genType(ty));
652 const operand = try c.genExpr(data.un);
653 return c.addBin(.cmp_ne, zero, operand, ty);
654 },
655 .pre_inc_expr => {
656 const operand = try c.genLval(data.un);
657 const val = try c.addUn(.load, operand, ty);
658 const one = try c.builder.addConstant(.one, try c.genType(ty));
659 const plus_one = try c.addBin(.add, val, one, ty);
660 try c.builder.addStore(operand, plus_one);
661 return plus_one;
662 },
663 .pre_dec_expr => {
664 const operand = try c.genLval(data.un);
665 const val = try c.addUn(.load, operand, ty);
666 const one = try c.builder.addConstant(.one, try c.genType(ty));
667 const plus_one = try c.addBin(.sub, val, one, ty);
668 try c.builder.addStore(operand, plus_one);
669 return plus_one;
670 },
671 .post_inc_expr => {
672 const operand = try c.genLval(data.un);
673 const val = try c.addUn(.load, operand, ty);
674 const one = try c.builder.addConstant(.one, try c.genType(ty));
675 const plus_one = try c.addBin(.add, val, one, ty);
676 try c.builder.addStore(operand, plus_one);
677 return val;
678 },
679 .post_dec_expr => {
680 const operand = try c.genLval(data.un);
681 const val = try c.addUn(.load, operand, ty);
682 const one = try c.builder.addConstant(.one, try c.genType(ty));
683 const plus_one = try c.addBin(.sub, val, one, ty);
684 try c.builder.addStore(operand, plus_one);
685 return val;
686 },
687 .paren_expr => return c.genExpr(data.un),
688 .decl_ref_expr => unreachable, // Lval expression.
689 .explicit_cast, .implicit_cast => switch (data.cast.kind) {
690 .no_op => return c.genExpr(data.cast.operand),
691 .to_void => {
692 _ = try c.genExpr(data.cast.operand);
693 return .none;
694 },
695 .lval_to_rval => {
696 const operand = try c.genLval(data.cast.operand);
697 return c.addUn(.load, operand, ty);
698 },
699 .function_to_pointer, .array_to_pointer => {
700 return c.genLval(data.cast.operand);
701 },
702 .int_cast => {
703 const operand = try c.genExpr(data.cast.operand);
704 const src_ty = c.node_ty[@intFromEnum(data.cast.operand)];
705 const src_bits = src_ty.bitSizeof(c.comp).?;
706 const dest_bits = ty.bitSizeof(c.comp).?;
707 if (src_bits == dest_bits) {
708 return operand;
709 } else if (src_bits < dest_bits) {
710 if (src_ty.isUnsignedInt(c.comp))
711 return c.addUn(.zext, operand, ty)
712 else
713 return c.addUn(.sext, operand, ty);
714 } else {
715 return c.addUn(.trunc, operand, ty);
716 }
717 },
718 .bool_to_int => {
719 const operand = try c.genExpr(data.cast.operand);
720 return c.addUn(.zext, operand, ty);
721 },
722 .pointer_to_bool, .int_to_bool, .float_to_bool => {
723 const lhs = try c.genExpr(data.cast.operand);
724 const rhs = try c.builder.addConstant(.zero, try c.genType(c.node_ty[@intFromEnum(node)]));
725 return c.builder.addInst(.cmp_ne, .{ .bin = .{ .lhs = lhs, .rhs = rhs } }, .i1);
726 },
727 .bitcast,
728 .pointer_to_int,
729 .bool_to_float,
730 .bool_to_pointer,
731 .int_to_float,
732 .complex_int_to_complex_float,
733 .int_to_pointer,
734 .float_to_int,
735 .complex_float_to_complex_int,
736 .complex_int_cast,
737 .complex_int_to_real,
738 .real_to_complex_int,
739 .float_cast,
740 .complex_float_cast,
741 .complex_float_to_real,
742 .real_to_complex_float,
743 .null_to_pointer,
744 .union_cast,
745 .vector_splat,
746 => return c.fail("TODO CodeGen gen CastKind {}\n", .{data.cast.kind}),
747 },
748 .binary_cond_expr => {
749 if (c.tree.value_map.get(data.if3.cond)) |cond| {
750 if (cond.toBool(c.comp)) {
751 c.cond_dummy_ref = try c.genExpr(data.if3.cond);
752 return c.genExpr(c.tree.data[data.if3.body]); // then
753 } else {
754 return c.genExpr(c.tree.data[data.if3.body + 1]); // else
755 }
756 }
757
758 const then_label = try c.builder.makeLabel("ternary.then");
759 const else_label = try c.builder.makeLabel("ternary.else");
760 const end_label = try c.builder.makeLabel("ternary.end");
761 const cond_ty = c.node_ty[@intFromEnum(data.if3.cond)];
762 {
763 const old_cond_dummy_ty = c.cond_dummy_ty;
764 defer c.cond_dummy_ty = old_cond_dummy_ty;
765 c.cond_dummy_ty = try c.genType(cond_ty);
766
767 try c.genBoolExpr(data.if3.cond, then_label, else_label);
768 }
769
770 try c.builder.startBlock(then_label);
771 if (c.builder.instructions.items(.ty)[@intFromEnum(c.cond_dummy_ref)] == .i1) {
772 c.cond_dummy_ref = try c.addUn(.zext, c.cond_dummy_ref, cond_ty);
773 }
774 const then_val = try c.genExpr(c.tree.data[data.if3.body]); // then
775 try c.builder.addJump(end_label);
776 const then_exit = c.builder.current_label;
777
778 try c.builder.startBlock(else_label);
779 const else_val = try c.genExpr(c.tree.data[data.if3.body + 1]); // else
780 const else_exit = c.builder.current_label;
781
782 try c.builder.startBlock(end_label);
783
784 var phi_buf: [2]Ir.Inst.Phi.Input = .{
785 .{ .value = then_val, .label = then_exit },
786 .{ .value = else_val, .label = else_exit },
787 };
788 return c.builder.addPhi(&phi_buf, try c.genType(ty));
789 },
790 .cond_dummy_expr => return c.cond_dummy_ref,
791 .cond_expr => {
792 if (c.tree.value_map.get(data.if3.cond)) |cond| {
793 if (cond.toBool(c.comp)) {
794 return c.genExpr(c.tree.data[data.if3.body]); // then
795 } else {
796 return c.genExpr(c.tree.data[data.if3.body + 1]); // else
797 }
798 }
799
800 const then_label = try c.builder.makeLabel("ternary.then");
801 const else_label = try c.builder.makeLabel("ternary.else");
802 const end_label = try c.builder.makeLabel("ternary.end");
803
804 try c.genBoolExpr(data.if3.cond, then_label, else_label);
805
806 try c.builder.startBlock(then_label);
807 const then_val = try c.genExpr(c.tree.data[data.if3.body]); // then
808 try c.builder.addJump(end_label);
809 const then_exit = c.builder.current_label;
810
811 try c.builder.startBlock(else_label);
812 const else_val = try c.genExpr(c.tree.data[data.if3.body + 1]); // else
813 const else_exit = c.builder.current_label;
814
815 try c.builder.startBlock(end_label);
816
817 var phi_buf: [2]Ir.Inst.Phi.Input = .{
818 .{ .value = then_val, .label = then_exit },
819 .{ .value = else_val, .label = else_exit },
820 };
821 return c.builder.addPhi(&phi_buf, try c.genType(ty));
822 },
823 .call_expr_one => if (data.bin.rhs == .none) {
824 return c.genCall(data.bin.lhs, &.{}, ty);
825 } else {
826 return c.genCall(data.bin.lhs, &.{data.bin.rhs}, ty);
827 },
828 .call_expr => {
829 return c.genCall(c.tree.data[data.range.start], c.tree.data[data.range.start + 1 .. data.range.end], ty);
830 },
831 .bool_or_expr => {
832 if (c.tree.value_map.get(data.bin.lhs)) |lhs| {
833 if (!lhs.toBool(c.comp)) {
834 return c.builder.addConstant(.one, try c.genType(ty));
835 }
836 return c.genExpr(data.bin.rhs);
837 }
838
839 const false_label = try c.builder.makeLabel("bool_false");
840 const exit_label = try c.builder.makeLabel("bool_exit");
841
842 const old_bool_end_label = c.bool_end_label;
843 defer c.bool_end_label = old_bool_end_label;
844 c.bool_end_label = exit_label;
845
846 const phi_nodes_top = c.phi_nodes.items.len;
847 defer c.phi_nodes.items.len = phi_nodes_top;
848
849 try c.genBoolExpr(data.bin.lhs, exit_label, false_label);
850
851 try c.builder.startBlock(false_label);
852 try c.genBoolExpr(data.bin.rhs, exit_label, exit_label);
853
854 try c.builder.startBlock(exit_label);
855
856 const phi = try c.builder.addPhi(c.phi_nodes.items[phi_nodes_top..], .i1);
857 return c.addUn(.zext, phi, ty);
858 },
859 .bool_and_expr => {
860 if (c.tree.value_map.get(data.bin.lhs)) |lhs| {
861 if (!lhs.toBool(c.comp)) {
862 return c.builder.addConstant(.zero, try c.genType(ty));
863 }
864 return c.genExpr(data.bin.rhs);
865 }
866
867 const true_label = try c.builder.makeLabel("bool_true");
868 const exit_label = try c.builder.makeLabel("bool_exit");
869
870 const old_bool_end_label = c.bool_end_label;
871 defer c.bool_end_label = old_bool_end_label;
872 c.bool_end_label = exit_label;
873
874 const phi_nodes_top = c.phi_nodes.items.len;
875 defer c.phi_nodes.items.len = phi_nodes_top;
876
877 try c.genBoolExpr(data.bin.lhs, true_label, exit_label);
878
879 try c.builder.startBlock(true_label);
880 try c.genBoolExpr(data.bin.rhs, exit_label, exit_label);
881
882 try c.builder.startBlock(exit_label);
883
884 const phi = try c.builder.addPhi(c.phi_nodes.items[phi_nodes_top..], .i1);
885 return c.addUn(.zext, phi, ty);
886 },
887 .builtin_choose_expr => {
888 const cond = c.tree.value_map.get(data.if3.cond).?;
889 if (cond.toBool(c.comp)) {
890 return c.genExpr(c.tree.data[data.if3.body]);
891 } else {
892 return c.genExpr(c.tree.data[data.if3.body + 1]);
893 }
894 },
895 .generic_expr_one => {
896 const index = @intFromEnum(data.bin.rhs);
897 switch (c.node_tag[index]) {
898 .generic_association_expr, .generic_default_expr => {
899 return c.genExpr(c.node_data[index].un);
900 },
901 else => unreachable,
902 }
903 },
904 .generic_expr => {
905 const index = @intFromEnum(c.tree.data[data.range.start + 1]);
906 switch (c.node_tag[index]) {
907 .generic_association_expr, .generic_default_expr => {
908 return c.genExpr(c.node_data[index].un);
909 },
910 else => unreachable,
911 }
912 },
913 .generic_association_expr, .generic_default_expr => unreachable,
914 .stmt_expr => switch (c.node_tag[@intFromEnum(data.un)]) {
915 .compound_stmt_two => {
916 const old_sym_len = c.symbols.items.len;
917 c.symbols.items.len = old_sym_len;
918
919 const stmt_data = c.node_data[@intFromEnum(data.un)];
920 if (stmt_data.bin.rhs == .none) return c.genExpr(stmt_data.bin.lhs);
921 try c.genStmt(stmt_data.bin.lhs);
922 return c.genExpr(stmt_data.bin.rhs);
923 },
924 .compound_stmt => {
925 const old_sym_len = c.symbols.items.len;
926 c.symbols.items.len = old_sym_len;
927
928 const stmt_data = c.node_data[@intFromEnum(data.un)];
929 for (c.tree.data[stmt_data.range.start .. stmt_data.range.end - 1]) |stmt| try c.genStmt(stmt);
930 return c.genExpr(c.tree.data[stmt_data.range.end]);
931 },
932 else => unreachable,
933 },
934 .builtin_call_expr_one => {
935 const name = c.tree.tokSlice(data.decl.name);
936 const builtin = c.comp.builtins.lookup(name).builtin;
937 if (data.decl.node == .none) {
938 return c.genBuiltinCall(builtin, &.{}, ty);
939 } else {
940 return c.genBuiltinCall(builtin, &.{data.decl.node}, ty);
941 }
942 },
943 .builtin_call_expr => {
944 const name_node_idx = c.tree.data[data.range.start];
945 const name = c.tree.tokSlice(@intFromEnum(name_node_idx));
946 const builtin = c.comp.builtins.lookup(name).builtin;
947 return c.genBuiltinCall(builtin, c.tree.data[data.range.start + 1 .. data.range.end], ty);
948 },
949 .addr_of_label,
950 .imag_expr,
951 .real_expr,
952 .sizeof_expr,
953 .special_builtin_call_one,
954 => return c.fail("TODO CodeGen.genExpr {}\n", .{c.node_tag[@intFromEnum(node)]}),
955 else => unreachable, // Not an expression.
956 }
957 return .none;
958}
959
960fn genLval(c: *CodeGen, node: NodeIndex) Error!Ir.Ref {
961 std.debug.assert(node != .none);
962 assert(c.tree.isLval(node));
963 const data = c.node_data[@intFromEnum(node)];
964 switch (c.node_tag[@intFromEnum(node)]) {
965 .string_literal_expr => {
966 const val = c.tree.value_map.get(node).?;
967 return c.builder.addConstant(val.ref(), .ptr);
968 },
969 .paren_expr => return c.genLval(data.un),
970 .decl_ref_expr => {
971 const slice = c.tree.tokSlice(data.decl_ref);
972 const name = try StrInt.intern(c.comp, slice);
973 var i = c.symbols.items.len;
974 while (i > 0) {
975 i -= 1;
976 if (c.symbols.items[i].name == name) {
977 return c.symbols.items[i].val;
978 }
979 }
980
981 const duped_name = try c.builder.arena.allocator().dupeZ(u8, slice);
982 const ref: Ir.Ref = @enumFromInt(c.builder.instructions.len);
983 try c.builder.instructions.append(c.builder.gpa, .{ .tag = .symbol, .data = .{ .label = duped_name }, .ty = .ptr });
984 return ref;
985 },
986 .deref_expr => return c.genExpr(data.un),
987 .compound_literal_expr => {
988 const ty = c.node_ty[@intFromEnum(node)];
989 const size: u32 = @intCast(ty.sizeof(c.comp).?); // TODO add error in parser
990 const @"align" = ty.alignof(c.comp);
991 const alloc = try c.builder.addAlloc(size, @"align");
992 try c.genInitializer(alloc, ty, data.un);
993 return alloc;
994 },
995 .builtin_choose_expr => {
996 const cond = c.tree.value_map.get(data.if3.cond).?;
997 if (cond.toBool(c.comp)) {
998 return c.genLval(c.tree.data[data.if3.body]);
999 } else {
1000 return c.genLval(c.tree.data[data.if3.body + 1]);
1001 }
1002 },
1003 .member_access_expr,
1004 .member_access_ptr_expr,
1005 .array_access_expr,
1006 .static_compound_literal_expr,
1007 .thread_local_compound_literal_expr,
1008 .static_thread_local_compound_literal_expr,
1009 => return c.fail("TODO CodeGen.genLval {}\n", .{c.node_tag[@intFromEnum(node)]}),
1010 else => unreachable, // Not an lval expression.
1011 }
1012}
1013
1014fn genBoolExpr(c: *CodeGen, base: NodeIndex, true_label: Ir.Ref, false_label: Ir.Ref) Error!void {
1015 var node = base;
1016 while (true) switch (c.node_tag[@intFromEnum(node)]) {
1017 .paren_expr => {
1018 node = c.node_data[@intFromEnum(node)].un;
1019 },
1020 else => break,
1021 };
1022
1023 const data = c.node_data[@intFromEnum(node)];
1024 switch (c.node_tag[@intFromEnum(node)]) {
1025 .bool_or_expr => {
1026 if (c.tree.value_map.get(data.bin.lhs)) |lhs| {
1027 if (lhs.toBool(c.comp)) {
1028 if (true_label == c.bool_end_label) {
1029 return c.addBoolPhi(!c.bool_invert);
1030 }
1031 return c.builder.addJump(true_label);
1032 }
1033 return c.genBoolExpr(data.bin.rhs, true_label, false_label);
1034 }
1035
1036 const new_false_label = try c.builder.makeLabel("bool_false");
1037 try c.genBoolExpr(data.bin.lhs, true_label, new_false_label);
1038 try c.builder.startBlock(new_false_label);
1039
1040 if (c.cond_dummy_ty) |ty| c.cond_dummy_ref = try c.builder.addConstant(.one, ty);
1041 return c.genBoolExpr(data.bin.rhs, true_label, false_label);
1042 },
1043 .bool_and_expr => {
1044 if (c.tree.value_map.get(data.bin.lhs)) |lhs| {
1045 if (!lhs.toBool(c.comp)) {
1046 if (false_label == c.bool_end_label) {
1047 return c.addBoolPhi(c.bool_invert);
1048 }
1049 return c.builder.addJump(false_label);
1050 }
1051 return c.genBoolExpr(data.bin.rhs, true_label, false_label);
1052 }
1053
1054 const new_true_label = try c.builder.makeLabel("bool_true");
1055 try c.genBoolExpr(data.bin.lhs, new_true_label, false_label);
1056 try c.builder.startBlock(new_true_label);
1057
1058 if (c.cond_dummy_ty) |ty| c.cond_dummy_ref = try c.builder.addConstant(.one, ty);
1059 return c.genBoolExpr(data.bin.rhs, true_label, false_label);
1060 },
1061 .bool_not_expr => {
1062 c.bool_invert = !c.bool_invert;
1063 defer c.bool_invert = !c.bool_invert;
1064
1065 if (c.cond_dummy_ty) |ty| c.cond_dummy_ref = try c.builder.addConstant(.zero, ty);
1066 return c.genBoolExpr(data.un, false_label, true_label);
1067 },
1068 .equal_expr => {
1069 const cmp = try c.genComparison(node, .cmp_eq);
1070 if (c.cond_dummy_ty != null) c.cond_dummy_ref = cmp;
1071 return c.addBranch(cmp, true_label, false_label);
1072 },
1073 .not_equal_expr => {
1074 const cmp = try c.genComparison(node, .cmp_ne);
1075 if (c.cond_dummy_ty != null) c.cond_dummy_ref = cmp;
1076 return c.addBranch(cmp, true_label, false_label);
1077 },
1078 .less_than_expr => {
1079 const cmp = try c.genComparison(node, .cmp_lt);
1080 if (c.cond_dummy_ty != null) c.cond_dummy_ref = cmp;
1081 return c.addBranch(cmp, true_label, false_label);
1082 },
1083 .less_than_equal_expr => {
1084 const cmp = try c.genComparison(node, .cmp_lte);
1085 if (c.cond_dummy_ty != null) c.cond_dummy_ref = cmp;
1086 return c.addBranch(cmp, true_label, false_label);
1087 },
1088 .greater_than_expr => {
1089 const cmp = try c.genComparison(node, .cmp_gt);
1090 if (c.cond_dummy_ty != null) c.cond_dummy_ref = cmp;
1091 return c.addBranch(cmp, true_label, false_label);
1092 },
1093 .greater_than_equal_expr => {
1094 const cmp = try c.genComparison(node, .cmp_gte);
1095 if (c.cond_dummy_ty != null) c.cond_dummy_ref = cmp;
1096 return c.addBranch(cmp, true_label, false_label);
1097 },
1098 .explicit_cast, .implicit_cast => switch (data.cast.kind) {
1099 .bool_to_int => {
1100 const operand = try c.genExpr(data.cast.operand);
1101 if (c.cond_dummy_ty != null) c.cond_dummy_ref = operand;
1102 return c.addBranch(operand, true_label, false_label);
1103 },
1104 else => {},
1105 },
1106 .binary_cond_expr => {
1107 if (c.tree.value_map.get(data.if3.cond)) |cond| {
1108 if (cond.toBool(c.comp)) {
1109 return c.genBoolExpr(c.tree.data[data.if3.body], true_label, false_label); // then
1110 } else {
1111 return c.genBoolExpr(c.tree.data[data.if3.body + 1], true_label, false_label); // else
1112 }
1113 }
1114
1115 const new_false_label = try c.builder.makeLabel("ternary.else");
1116 try c.genBoolExpr(data.if3.cond, true_label, new_false_label);
1117
1118 try c.builder.startBlock(new_false_label);
1119 if (c.cond_dummy_ty) |ty| c.cond_dummy_ref = try c.builder.addConstant(.one, ty);
1120 return c.genBoolExpr(c.tree.data[data.if3.body + 1], true_label, false_label); // else
1121 },
1122 .cond_expr => {
1123 if (c.tree.value_map.get(data.if3.cond)) |cond| {
1124 if (cond.toBool(c.comp)) {
1125 return c.genBoolExpr(c.tree.data[data.if3.body], true_label, false_label); // then
1126 } else {
1127 return c.genBoolExpr(c.tree.data[data.if3.body + 1], true_label, false_label); // else
1128 }
1129 }
1130
1131 const new_true_label = try c.builder.makeLabel("ternary.then");
1132 const new_false_label = try c.builder.makeLabel("ternary.else");
1133 try c.genBoolExpr(data.if3.cond, new_true_label, new_false_label);
1134
1135 try c.builder.startBlock(new_true_label);
1136 try c.genBoolExpr(c.tree.data[data.if3.body], true_label, false_label); // then
1137 try c.builder.startBlock(new_false_label);
1138 if (c.cond_dummy_ty) |ty| c.cond_dummy_ref = try c.builder.addConstant(.one, ty);
1139 return c.genBoolExpr(c.tree.data[data.if3.body + 1], true_label, false_label); // else
1140 },
1141 else => {},
1142 }
1143
1144 if (c.tree.value_map.get(node)) |value| {
1145 if (value.toBool(c.comp)) {
1146 if (true_label == c.bool_end_label) {
1147 return c.addBoolPhi(!c.bool_invert);
1148 }
1149 return c.builder.addJump(true_label);
1150 } else {
1151 if (false_label == c.bool_end_label) {
1152 return c.addBoolPhi(c.bool_invert);
1153 }
1154 return c.builder.addJump(false_label);
1155 }
1156 }
1157
1158 // Assume int operand.
1159 const lhs = try c.genExpr(node);
1160 const rhs = try c.builder.addConstant(.zero, try c.genType(c.node_ty[@intFromEnum(node)]));
1161 const cmp = try c.builder.addInst(.cmp_ne, .{ .bin = .{ .lhs = lhs, .rhs = rhs } }, .i1);
1162 if (c.cond_dummy_ty != null) c.cond_dummy_ref = cmp;
1163 try c.addBranch(cmp, true_label, false_label);
1164}
1165
1166fn genBuiltinCall(c: *CodeGen, builtin: Builtin, arg_nodes: []const NodeIndex, ty: Type) Error!Ir.Ref {
1167 _ = arg_nodes;
1168 _ = ty;
1169 return c.fail("TODO CodeGen.genBuiltinCall {s}\n", .{Builtin.nameFromTag(builtin.tag).span()});
1170}
1171
1172fn genCall(c: *CodeGen, fn_node: NodeIndex, arg_nodes: []const NodeIndex, ty: Type) Error!Ir.Ref {
1173 // Detect direct calls.
1174 const fn_ref = blk: {
1175 const data = c.node_data[@intFromEnum(fn_node)];
1176 if (c.node_tag[@intFromEnum(fn_node)] != .implicit_cast or data.cast.kind != .function_to_pointer) {
1177 break :blk try c.genExpr(fn_node);
1178 }
1179
1180 var cur = @intFromEnum(data.cast.operand);
1181 while (true) switch (c.node_tag[cur]) {
1182 .paren_expr, .addr_of_expr, .deref_expr => {
1183 cur = @intFromEnum(c.node_data[cur].un);
1184 },
1185 .implicit_cast => {
1186 const cast = c.node_data[cur].cast;
1187 if (cast.kind != .function_to_pointer) {
1188 break :blk try c.genExpr(fn_node);
1189 }
1190 cur = @intFromEnum(cast.operand);
1191 },
1192 .decl_ref_expr => {
1193 const slice = c.tree.tokSlice(c.node_data[cur].decl_ref);
1194 const name = try StrInt.intern(c.comp, slice);
1195 var i = c.symbols.items.len;
1196 while (i > 0) {
1197 i -= 1;
1198 if (c.symbols.items[i].name == name) {
1199 break :blk try c.genExpr(fn_node);
1200 }
1201 }
1202
1203 const duped_name = try c.builder.arena.allocator().dupeZ(u8, slice);
1204 const ref: Ir.Ref = @enumFromInt(c.builder.instructions.len);
1205 try c.builder.instructions.append(c.builder.gpa, .{ .tag = .symbol, .data = .{ .label = duped_name }, .ty = .ptr });
1206 break :blk ref;
1207 },
1208 else => break :blk try c.genExpr(fn_node),
1209 };
1210 };
1211
1212 const args = try c.builder.arena.allocator().alloc(Ir.Ref, arg_nodes.len);
1213 for (arg_nodes, args) |node, *arg| {
1214 // TODO handle calling convention here
1215 arg.* = try c.genExpr(node);
1216 }
1217 // TODO handle variadic call
1218 const call = try c.builder.arena.allocator().create(Ir.Inst.Call);
1219 call.* = .{
1220 .func = fn_ref,
1221 .args_len = @intCast(args.len),
1222 .args_ptr = args.ptr,
1223 };
1224 return c.builder.addInst(.call, .{ .call = call }, try c.genType(ty));
1225}
1226
1227fn genCompoundAssign(c: *CodeGen, node: NodeIndex, tag: Ir.Inst.Tag) Error!Ir.Ref {
1228 const bin = c.node_data[@intFromEnum(node)].bin;
1229 const ty = c.node_ty[@intFromEnum(node)];
1230 const rhs = try c.genExpr(bin.rhs);
1231 const lhs = try c.genLval(bin.lhs);
1232 const res = try c.addBin(tag, lhs, rhs, ty);
1233 try c.builder.addStore(lhs, res);
1234 return res;
1235}
1236
1237fn genBinOp(c: *CodeGen, node: NodeIndex, tag: Ir.Inst.Tag) Error!Ir.Ref {
1238 const bin = c.node_data[@intFromEnum(node)].bin;
1239 const ty = c.node_ty[@intFromEnum(node)];
1240 const lhs = try c.genExpr(bin.lhs);
1241 const rhs = try c.genExpr(bin.rhs);
1242 return c.addBin(tag, lhs, rhs, ty);
1243}
1244
1245fn genComparison(c: *CodeGen, node: NodeIndex, tag: Ir.Inst.Tag) Error!Ir.Ref {
1246 const bin = c.node_data[@intFromEnum(node)].bin;
1247 const lhs = try c.genExpr(bin.lhs);
1248 const rhs = try c.genExpr(bin.rhs);
1249
1250 return c.builder.addInst(tag, .{ .bin = .{ .lhs = lhs, .rhs = rhs } }, .i1);
1251}
1252
1253fn genPtrArithmetic(c: *CodeGen, ptr: Ir.Ref, offset: Ir.Ref, offset_ty: Type, ty: Type) Error!Ir.Ref {
1254 // TODO consider adding a getelemptr instruction
1255 const size = ty.elemType().sizeof(c.comp).?;
1256 if (size == 1) {
1257 return c.builder.addInst(.add, .{ .bin = .{ .lhs = ptr, .rhs = offset } }, try c.genType(ty));
1258 }
1259
1260 const size_inst = try c.builder.addConstant((try Value.int(size, c.comp)).ref(), try c.genType(offset_ty));
1261 const offset_inst = try c.addBin(.mul, offset, size_inst, offset_ty);
1262 return c.addBin(.add, ptr, offset_inst, offset_ty);
1263}
1264
1265fn genInitializer(c: *CodeGen, ptr: Ir.Ref, dest_ty: Type, initializer: NodeIndex) Error!void {
1266 std.debug.assert(initializer != .none);
1267 switch (c.node_tag[@intFromEnum(initializer)]) {
1268 .array_init_expr_two,
1269 .array_init_expr,
1270 .struct_init_expr_two,
1271 .struct_init_expr,
1272 .union_init_expr,
1273 .array_filler_expr,
1274 .default_init_expr,
1275 => return c.fail("TODO CodeGen.genInitializer {}\n", .{c.node_tag[@intFromEnum(initializer)]}),
1276 .string_literal_expr => {
1277 const val = c.tree.value_map.get(initializer).?;
1278 const str_ptr = try c.builder.addConstant(val.ref(), .ptr);
1279 if (dest_ty.isArray()) {
1280 return c.fail("TODO memcpy\n", .{});
1281 } else {
1282 try c.builder.addStore(ptr, str_ptr);
1283 }
1284 },
1285 else => {
1286 const res = try c.genExpr(initializer);
1287 try c.builder.addStore(ptr, res);
1288 },
1289 }
1290}
1291
1292fn genVar(c: *CodeGen, decl: NodeIndex) Error!void {
1293 _ = decl;
1294 return c.fail("TODO CodeGen.genVar\n", .{});
1295}
lib/compiler/aro/aro/Compilation.zig deleted-1740
...@@ -1,1740 +0,0 @@
1const std = @import("std");
2const Allocator = mem.Allocator;
3const assert = std.debug.assert;
4const EpochSeconds = std.time.epoch.EpochSeconds;
5const mem = std.mem;
6const Interner = @import("../backend.zig").Interner;
7const Builtins = @import("Builtins.zig");
8const Builtin = Builtins.Builtin;
9const Diagnostics = @import("Diagnostics.zig");
10const LangOpts = @import("LangOpts.zig");
11const Source = @import("Source.zig");
12const Tokenizer = @import("Tokenizer.zig");
13const Token = Tokenizer.Token;
14const Type = @import("Type.zig");
15const Pragma = @import("Pragma.zig");
16const StrInt = @import("StringInterner.zig");
17const record_layout = @import("record_layout.zig");
18const target_util = @import("target.zig");
19
20pub const Error = error{
21 /// A fatal error has ocurred and compilation has stopped.
22 FatalError,
23} || Allocator.Error;
24
25pub const bit_int_max_bits = std.math.maxInt(u16);
26const path_buf_stack_limit = 1024;
27
28/// Environment variables used during compilation / linking.
29pub const Environment = struct {
30 /// Directory to use for temporary files
31 /// TODO: not implemented yet
32 tmpdir: ?[]const u8 = null,
33
34 /// PATH environment variable used to search for programs
35 path: ?[]const u8 = null,
36
37 /// Directories to try when searching for subprograms.
38 /// TODO: not implemented yet
39 compiler_path: ?[]const u8 = null,
40
41 /// Directories to try when searching for special linker files, if compiling for the native target
42 /// TODO: not implemented yet
43 library_path: ?[]const u8 = null,
44
45 /// List of directories to be searched as if specified with -I, but after any paths given with -I options on the command line
46 /// Used regardless of the language being compiled
47 /// TODO: not implemented yet
48 cpath: ?[]const u8 = null,
49
50 /// List of directories to be searched as if specified with -I, but after any paths given with -I options on the command line
51 /// Used if the language being compiled is C
52 /// TODO: not implemented yet
53 c_include_path: ?[]const u8 = null,
54
55 /// UNIX timestamp to be used instead of the current date and time in the __DATE__ and __TIME__ macros
56 source_date_epoch: ?[]const u8 = null,
57
58 /// Load all of the environment variables using the std.process API. Do not use if using Aro as a shared library on Linux without libc
59 /// See https://github.com/ziglang/zig/issues/4524
60 pub fn loadAll(allocator: std.mem.Allocator) !Environment {
61 var env: Environment = .{};
62 errdefer env.deinit(allocator);
63
64 inline for (@typeInfo(@TypeOf(env)).@"struct".fields) |field| {
65 std.debug.assert(@field(env, field.name) == null);
66
67 var env_var_buf: [field.name.len]u8 = undefined;
68 const env_var_name = std.ascii.upperString(&env_var_buf, field.name);
69 const val: ?[]const u8 = std.process.getEnvVarOwned(allocator, env_var_name) catch |err| switch (err) {
70 error.OutOfMemory => |e| return e,
71 error.EnvironmentVariableNotFound => null,
72 error.InvalidWtf8 => null,
73 };
74 @field(env, field.name) = val;
75 }
76 return env;
77 }
78
79 /// Use this only if environment slices were allocated with `allocator` (such as via `loadAll`)
80 pub fn deinit(self: *Environment, allocator: std.mem.Allocator) void {
81 inline for (@typeInfo(@TypeOf(self.*)).@"struct".fields) |field| {
82 if (@field(self, field.name)) |slice| {
83 allocator.free(slice);
84 }
85 }
86 self.* = undefined;
87 }
88};
89
90const Compilation = @This();
91
92gpa: Allocator,
93diagnostics: Diagnostics,
94
95environment: Environment = .{},
96sources: std.StringArrayHashMapUnmanaged(Source) = .empty,
97include_dirs: std.ArrayListUnmanaged([]const u8) = .empty,
98system_include_dirs: std.ArrayListUnmanaged([]const u8) = .empty,
99target: std.Target = @import("builtin").target,
100pragma_handlers: std.StringArrayHashMapUnmanaged(*Pragma) = .empty,
101langopts: LangOpts = .{},
102generated_buf: std.ArrayListUnmanaged(u8) = .empty,
103builtins: Builtins = .{},
104types: struct {
105 wchar: Type = undefined,
106 uint_least16_t: Type = undefined,
107 uint_least32_t: Type = undefined,
108 ptrdiff: Type = undefined,
109 size: Type = undefined,
110 va_list: Type = undefined,
111 pid_t: Type = undefined,
112 ns_constant_string: struct {
113 ty: Type = undefined,
114 record: Type.Record = undefined,
115 fields: [4]Type.Record.Field = undefined,
116 int_ty: Type = .{ .specifier = .int, .qual = .{ .@"const" = true } },
117 char_ty: Type = .{ .specifier = .char, .qual = .{ .@"const" = true } },
118 } = .{},
119 file: Type = .{ .specifier = .invalid },
120 jmp_buf: Type = .{ .specifier = .invalid },
121 sigjmp_buf: Type = .{ .specifier = .invalid },
122 ucontext_t: Type = .{ .specifier = .invalid },
123 intmax: Type = .{ .specifier = .invalid },
124 intptr: Type = .{ .specifier = .invalid },
125 int16: Type = .{ .specifier = .invalid },
126 int64: Type = .{ .specifier = .invalid },
127} = .{},
128string_interner: StrInt = .{},
129interner: Interner = .{},
130/// If this is not null, the directory containing the specified Source will be searched for includes
131/// Used by MS extensions which allow searching for includes relative to the directory of the main source file.
132ms_cwd_source_id: ?Source.Id = null,
133cwd: std.fs.Dir,
134
135pub fn init(gpa: Allocator, cwd: std.fs.Dir) Compilation {
136 return .{
137 .gpa = gpa,
138 .diagnostics = Diagnostics.init(gpa),
139 .cwd = cwd,
140 };
141}
142
143/// Initialize Compilation with default environment,
144/// pragma handlers and emulation mode set to target.
145pub fn initDefault(gpa: Allocator, cwd: std.fs.Dir) !Compilation {
146 var comp: Compilation = .{
147 .gpa = gpa,
148 .environment = try Environment.loadAll(gpa),
149 .diagnostics = Diagnostics.init(gpa),
150 .cwd = cwd,
151 };
152 errdefer comp.deinit();
153 try comp.addDefaultPragmaHandlers();
154 comp.langopts.setEmulatedCompiler(target_util.systemCompiler(comp.target));
155 return comp;
156}
157
158pub fn deinit(comp: *Compilation) void {
159 for (comp.pragma_handlers.values()) |pragma| {
160 pragma.deinit(pragma, comp);
161 }
162 for (comp.sources.values()) |source| {
163 comp.gpa.free(source.path);
164 comp.gpa.free(source.buf);
165 comp.gpa.free(source.splice_locs);
166 }
167 comp.sources.deinit(comp.gpa);
168 comp.diagnostics.deinit();
169 comp.include_dirs.deinit(comp.gpa);
170 for (comp.system_include_dirs.items) |path| comp.gpa.free(path);
171 comp.system_include_dirs.deinit(comp.gpa);
172 comp.pragma_handlers.deinit(comp.gpa);
173 comp.generated_buf.deinit(comp.gpa);
174 comp.builtins.deinit(comp.gpa);
175 comp.string_interner.deinit(comp.gpa);
176 comp.interner.deinit(comp.gpa);
177 comp.environment.deinit(comp.gpa);
178}
179
180pub fn getSourceEpoch(self: *const Compilation, max: i64) !?i64 {
181 const provided = self.environment.source_date_epoch orelse return null;
182 const parsed = std.fmt.parseInt(i64, provided, 10) catch return error.InvalidEpoch;
183 if (parsed < 0 or parsed > max) return error.InvalidEpoch;
184 return parsed;
185}
186
187/// Dec 31 9999 23:59:59
188const max_timestamp = 253402300799;
189
190fn getTimestamp(comp: *Compilation) !u47 {
191 const provided: ?i64 = comp.getSourceEpoch(max_timestamp) catch blk: {
192 try comp.addDiagnostic(.{
193 .tag = .invalid_source_epoch,
194 .loc = .{ .id = .unused, .byte_offset = 0, .line = 0 },
195 }, &.{});
196 break :blk null;
197 };
198 const timestamp = provided orelse std.time.timestamp();
199 return @intCast(std.math.clamp(timestamp, 0, max_timestamp));
200}
201
202fn generateDateAndTime(w: anytype, timestamp: u47) !void {
203 const epoch_seconds = EpochSeconds{ .secs = timestamp };
204 const epoch_day = epoch_seconds.getEpochDay();
205 const day_seconds = epoch_seconds.getDaySeconds();
206 const year_day = epoch_day.calculateYearDay();
207 const month_day = year_day.calculateMonthDay();
208
209 const month_names = [_][]const u8{ "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" };
210 std.debug.assert(std.time.epoch.Month.jan.numeric() == 1);
211
212 const month_name = month_names[month_day.month.numeric() - 1];
213 try w.print("#define __DATE__ \"{s} {d: >2} {d}\"\n", .{
214 month_name,
215 month_day.day_index + 1,
216 year_day.year,
217 });
218 try w.print("#define __TIME__ \"{d:0>2}:{d:0>2}:{d:0>2}\"\n", .{
219 day_seconds.getHoursIntoDay(),
220 day_seconds.getMinutesIntoHour(),
221 day_seconds.getSecondsIntoMinute(),
222 });
223
224 const day_names = [_][]const u8{ "Mon", "Tue", "Wed", "Thu", "Fri", "Sat", "Sun" };
225 const day_name = day_names[@intCast((epoch_day.day + 3) % 7)];
226 try w.print("#define __TIMESTAMP__ \"{s} {s} {d: >2} {d:0>2}:{d:0>2}:{d:0>2} {d}\"\n", .{
227 day_name,
228 month_name,
229 month_day.day_index + 1,
230 day_seconds.getHoursIntoDay(),
231 day_seconds.getMinutesIntoHour(),
232 day_seconds.getSecondsIntoMinute(),
233 year_day.year,
234 });
235}
236
237/// Which set of system defines to generate via generateBuiltinMacros
238pub const SystemDefinesMode = enum {
239 /// Only define macros required by the C standard (date/time macros and those beginning with `__STDC`)
240 no_system_defines,
241 /// Define the standard set of system macros
242 include_system_defines,
243};
244
245fn generateSystemDefines(comp: *Compilation, w: anytype) !void {
246 const ptr_width = comp.target.ptrBitWidth();
247
248 if (comp.langopts.gnuc_version > 0) {
249 try w.print("#define __GNUC__ {d}\n", .{comp.langopts.gnuc_version / 10_000});
250 try w.print("#define __GNUC_MINOR__ {d}\n", .{comp.langopts.gnuc_version / 100 % 100});
251 try w.print("#define __GNUC_PATCHLEVEL__ {d}\n", .{comp.langopts.gnuc_version % 100});
252 }
253
254 // os macros
255 switch (comp.target.os.tag) {
256 .linux => try w.writeAll(
257 \\#define linux 1
258 \\#define __linux 1
259 \\#define __linux__ 1
260 \\
261 ),
262 .windows => if (ptr_width == 32) try w.writeAll(
263 \\#define WIN32 1
264 \\#define _WIN32 1
265 \\#define __WIN32 1
266 \\#define __WIN32__ 1
267 \\
268 ) else try w.writeAll(
269 \\#define WIN32 1
270 \\#define WIN64 1
271 \\#define _WIN32 1
272 \\#define _WIN64 1
273 \\#define __WIN32 1
274 \\#define __WIN64 1
275 \\#define __WIN32__ 1
276 \\#define __WIN64__ 1
277 \\
278 ),
279 .freebsd => try w.print("#define __FreeBSD__ {d}\n", .{comp.target.os.version_range.semver.min.major}),
280 .netbsd => try w.writeAll("#define __NetBSD__ 1\n"),
281 .openbsd => try w.writeAll("#define __OpenBSD__ 1\n"),
282 .dragonfly => try w.writeAll("#define __DragonFly__ 1\n"),
283 .solaris => try w.writeAll(
284 \\#define sun 1
285 \\#define __sun 1
286 \\
287 ),
288 .macos => try w.writeAll(
289 \\#define __APPLE__ 1
290 \\#define __MACH__ 1
291 \\
292 ),
293 else => {},
294 }
295
296 // unix and other additional os macros
297 switch (comp.target.os.tag) {
298 .freebsd,
299 .netbsd,
300 .openbsd,
301 .dragonfly,
302 .linux,
303 => try w.writeAll(
304 \\#define unix 1
305 \\#define __unix 1
306 \\#define __unix__ 1
307 \\
308 ),
309 else => {},
310 }
311 if (comp.target.isAndroid()) {
312 try w.writeAll("#define __ANDROID__ 1\n");
313 }
314
315 // architecture macros
316 switch (comp.target.cpu.arch) {
317 .x86_64 => try w.writeAll(
318 \\#define __amd64__ 1
319 \\#define __amd64 1
320 \\#define __x86_64 1
321 \\#define __x86_64__ 1
322 \\
323 ),
324 .x86 => try w.writeAll(
325 \\#define i386 1
326 \\#define __i386 1
327 \\#define __i386__ 1
328 \\
329 ),
330 .mips,
331 .mipsel,
332 .mips64,
333 .mips64el,
334 => try w.writeAll(
335 \\#define __mips__ 1
336 \\#define mips 1
337 \\
338 ),
339 .powerpc,
340 .powerpcle,
341 => try w.writeAll(
342 \\#define __powerpc__ 1
343 \\#define __POWERPC__ 1
344 \\#define __ppc__ 1
345 \\#define __PPC__ 1
346 \\#define _ARCH_PPC 1
347 \\
348 ),
349 .powerpc64,
350 .powerpc64le,
351 => try w.writeAll(
352 \\#define __powerpc 1
353 \\#define __powerpc__ 1
354 \\#define __powerpc64__ 1
355 \\#define __POWERPC__ 1
356 \\#define __ppc__ 1
357 \\#define __ppc64__ 1
358 \\#define __PPC__ 1
359 \\#define __PPC64__ 1
360 \\#define _ARCH_PPC 1
361 \\#define _ARCH_PPC64 1
362 \\
363 ),
364 .sparc64 => try w.writeAll(
365 \\#define __sparc__ 1
366 \\#define __sparc 1
367 \\#define __sparc_v9__ 1
368 \\
369 ),
370 .sparc => try w.writeAll(
371 \\#define __sparc__ 1
372 \\#define __sparc 1
373 \\
374 ),
375 .arm, .armeb => try w.writeAll(
376 \\#define __arm__ 1
377 \\#define __arm 1
378 \\
379 ),
380 .thumb, .thumbeb => try w.writeAll(
381 \\#define __arm__ 1
382 \\#define __arm 1
383 \\#define __thumb__ 1
384 \\
385 ),
386 .aarch64, .aarch64_be => try w.writeAll("#define __aarch64__ 1\n"),
387 .msp430 => try w.writeAll(
388 \\#define MSP430 1
389 \\#define __MSP430__ 1
390 \\
391 ),
392 else => {},
393 }
394
395 if (comp.target.os.tag != .windows) switch (ptr_width) {
396 64 => try w.writeAll(
397 \\#define _LP64 1
398 \\#define __LP64__ 1
399 \\
400 ),
401 32 => try w.writeAll("#define _ILP32 1\n"),
402 else => {},
403 };
404
405 try w.writeAll(
406 \\#define __ORDER_LITTLE_ENDIAN__ 1234
407 \\#define __ORDER_BIG_ENDIAN__ 4321
408 \\#define __ORDER_PDP_ENDIAN__ 3412
409 \\
410 );
411 if (comp.target.cpu.arch.endian() == .little) try w.writeAll(
412 \\#define __BYTE_ORDER__ __ORDER_LITTLE_ENDIAN__
413 \\#define __LITTLE_ENDIAN__ 1
414 \\
415 ) else try w.writeAll(
416 \\#define __BYTE_ORDER__ __ORDER_BIG_ENDIAN__
417 \\#define __BIG_ENDIAN__ 1
418 \\
419 );
420
421 // atomics
422 try w.writeAll(
423 \\#define __ATOMIC_RELAXED 0
424 \\#define __ATOMIC_CONSUME 1
425 \\#define __ATOMIC_ACQUIRE 2
426 \\#define __ATOMIC_RELEASE 3
427 \\#define __ATOMIC_ACQ_REL 4
428 \\#define __ATOMIC_SEQ_CST 5
429 \\
430 );
431
432 // TODO: Set these to target-specific constants depending on backend capabilities
433 // For now they are just set to the "may be lock-free" value
434 try w.writeAll(
435 \\#define __ATOMIC_BOOL_LOCK_FREE 1
436 \\#define __ATOMIC_CHAR_LOCK_FREE 1
437 \\#define __ATOMIC_CHAR16_T_LOCK_FREE 1
438 \\#define __ATOMIC_CHAR32_T_LOCK_FREE 1
439 \\#define __ATOMIC_WCHAR_T_LOCK_FREE 1
440 \\#define __ATOMIC_SHORT_LOCK_FREE 1
441 \\#define __ATOMIC_INT_LOCK_FREE 1
442 \\#define __ATOMIC_LONG_LOCK_FREE 1
443 \\#define __ATOMIC_LLONG_LOCK_FREE 1
444 \\#define __ATOMIC_POINTER_LOCK_FREE 1
445 \\
446 );
447 if (comp.langopts.hasChar8_T()) {
448 try w.writeAll("#define __ATOMIC_CHAR8_T_LOCK_FREE 1\n");
449 }
450
451 // types
452 if (comp.getCharSignedness() == .unsigned) try w.writeAll("#define __CHAR_UNSIGNED__ 1\n");
453 try w.writeAll("#define __CHAR_BIT__ 8\n");
454
455 // int maxs
456 try comp.generateIntWidth(w, "BOOL", .{ .specifier = .bool });
457 try comp.generateIntMaxAndWidth(w, "SCHAR", .{ .specifier = .schar });
458 try comp.generateIntMaxAndWidth(w, "SHRT", .{ .specifier = .short });
459 try comp.generateIntMaxAndWidth(w, "INT", .{ .specifier = .int });
460 try comp.generateIntMaxAndWidth(w, "LONG", .{ .specifier = .long });
461 try comp.generateIntMaxAndWidth(w, "LONG_LONG", .{ .specifier = .long_long });
462 try comp.generateIntMaxAndWidth(w, "WCHAR", comp.types.wchar);
463 // try comp.generateIntMax(w, "WINT", comp.types.wchar);
464 try comp.generateIntMaxAndWidth(w, "INTMAX", comp.types.intmax);
465 try comp.generateIntMaxAndWidth(w, "SIZE", comp.types.size);
466 try comp.generateIntMaxAndWidth(w, "UINTMAX", comp.types.intmax.makeIntegerUnsigned());
467 try comp.generateIntMaxAndWidth(w, "PTRDIFF", comp.types.ptrdiff);
468 try comp.generateIntMaxAndWidth(w, "INTPTR", comp.types.intptr);
469 try comp.generateIntMaxAndWidth(w, "UINTPTR", comp.types.intptr.makeIntegerUnsigned());
470 try comp.generateIntMaxAndWidth(w, "SIG_ATOMIC", target_util.sigAtomicType(comp.target));
471
472 // int widths
473 try w.print("#define __BITINT_MAXWIDTH__ {d}\n", .{bit_int_max_bits});
474
475 // sizeof types
476 try comp.generateSizeofType(w, "__SIZEOF_FLOAT__", .{ .specifier = .float });
477 try comp.generateSizeofType(w, "__SIZEOF_DOUBLE__", .{ .specifier = .double });
478 try comp.generateSizeofType(w, "__SIZEOF_LONG_DOUBLE__", .{ .specifier = .long_double });
479 try comp.generateSizeofType(w, "__SIZEOF_SHORT__", .{ .specifier = .short });
480 try comp.generateSizeofType(w, "__SIZEOF_INT__", .{ .specifier = .int });
481 try comp.generateSizeofType(w, "__SIZEOF_LONG__", .{ .specifier = .long });
482 try comp.generateSizeofType(w, "__SIZEOF_LONG_LONG__", .{ .specifier = .long_long });
483 try comp.generateSizeofType(w, "__SIZEOF_POINTER__", .{ .specifier = .pointer });
484 try comp.generateSizeofType(w, "__SIZEOF_PTRDIFF_T__", comp.types.ptrdiff);
485 try comp.generateSizeofType(w, "__SIZEOF_SIZE_T__", comp.types.size);
486 try comp.generateSizeofType(w, "__SIZEOF_WCHAR_T__", comp.types.wchar);
487 // try comp.generateSizeofType(w, "__SIZEOF_WINT_T__", .{ .specifier = .pointer });
488
489 if (target_util.hasInt128(comp.target)) {
490 try comp.generateSizeofType(w, "__SIZEOF_INT128__", .{ .specifier = .int128 });
491 }
492
493 // various int types
494 const mapper = comp.string_interner.getSlowTypeMapper();
495 try generateTypeMacro(w, mapper, "__INTPTR_TYPE__", comp.types.intptr, comp.langopts);
496 try generateTypeMacro(w, mapper, "__UINTPTR_TYPE__", comp.types.intptr.makeIntegerUnsigned(), comp.langopts);
497
498 try generateTypeMacro(w, mapper, "__INTMAX_TYPE__", comp.types.intmax, comp.langopts);
499 try comp.generateSuffixMacro("__INTMAX", w, comp.types.intptr);
500
501 try generateTypeMacro(w, mapper, "__UINTMAX_TYPE__", comp.types.intmax.makeIntegerUnsigned(), comp.langopts);
502 try comp.generateSuffixMacro("__UINTMAX", w, comp.types.intptr.makeIntegerUnsigned());
503
504 try generateTypeMacro(w, mapper, "__PTRDIFF_TYPE__", comp.types.ptrdiff, comp.langopts);
505 try generateTypeMacro(w, mapper, "__SIZE_TYPE__", comp.types.size, comp.langopts);
506 try generateTypeMacro(w, mapper, "__WCHAR_TYPE__", comp.types.wchar, comp.langopts);
507 try generateTypeMacro(w, mapper, "__CHAR16_TYPE__", comp.types.uint_least16_t, comp.langopts);
508 try generateTypeMacro(w, mapper, "__CHAR32_TYPE__", comp.types.uint_least32_t, comp.langopts);
509
510 try comp.generateExactWidthTypes(w, mapper);
511 try comp.generateFastAndLeastWidthTypes(w, mapper);
512
513 if (target_util.FPSemantics.halfPrecisionType(comp.target)) |half| {
514 try generateFloatMacros(w, "FLT16", half, "F16");
515 }
516 try generateFloatMacros(w, "FLT", target_util.FPSemantics.forType(.float, comp.target), "F");
517 try generateFloatMacros(w, "DBL", target_util.FPSemantics.forType(.double, comp.target), "");
518 try generateFloatMacros(w, "LDBL", target_util.FPSemantics.forType(.longdouble, comp.target), "L");
519
520 // TODO: clang treats __FLT_EVAL_METHOD__ as a special-cased macro because evaluating it within a scope
521 // where `#pragma clang fp eval_method(X)` has been called produces an error diagnostic.
522 const flt_eval_method = comp.langopts.fp_eval_method orelse target_util.defaultFpEvalMethod(comp.target);
523 try w.print("#define __FLT_EVAL_METHOD__ {d}\n", .{@intFromEnum(flt_eval_method)});
524
525 try w.writeAll(
526 \\#define __FLT_RADIX__ 2
527 \\#define __DECIMAL_DIG__ __LDBL_DECIMAL_DIG__
528 \\
529 );
530}
531
532/// Generate builtin macros that will be available to each source file.
533pub fn generateBuiltinMacros(comp: *Compilation, system_defines_mode: SystemDefinesMode) !Source {
534 try comp.generateBuiltinTypes();
535
536 var buf = std.ArrayList(u8).init(comp.gpa);
537 defer buf.deinit();
538
539 if (system_defines_mode == .include_system_defines) {
540 try buf.appendSlice(
541 \\#define __VERSION__ "Aro
542 ++ " " ++ @import("../backend.zig").version_str ++ "\"\n" ++
543 \\#define __Aro__
544 \\
545 );
546 }
547
548 try buf.appendSlice("#define __STDC__ 1\n");
549 try buf.writer().print("#define __STDC_HOSTED__ {d}\n", .{@intFromBool(comp.target.os.tag != .freestanding)});
550
551 // standard macros
552 try buf.appendSlice(
553 \\#define __STDC_NO_COMPLEX__ 1
554 \\#define __STDC_NO_THREADS__ 1
555 \\#define __STDC_NO_VLA__ 1
556 \\#define __STDC_UTF_16__ 1
557 \\#define __STDC_UTF_32__ 1
558 \\#define __STDC_EMBED_NOT_FOUND__ 0
559 \\#define __STDC_EMBED_FOUND__ 1
560 \\#define __STDC_EMBED_EMPTY__ 2
561 \\
562 );
563 if (comp.langopts.standard.StdCVersionMacro()) |stdc_version| {
564 try buf.appendSlice("#define __STDC_VERSION__ ");
565 try buf.appendSlice(stdc_version);
566 try buf.append('\n');
567 }
568
569 // timestamps
570 const timestamp = try comp.getTimestamp();
571 try generateDateAndTime(buf.writer(), timestamp);
572
573 if (system_defines_mode == .include_system_defines) {
574 try comp.generateSystemDefines(buf.writer());
575 }
576
577 return comp.addSourceFromBuffer("<builtin>", buf.items);
578}
579
580fn generateFloatMacros(w: anytype, prefix: []const u8, semantics: target_util.FPSemantics, ext: []const u8) !void {
581 const denormMin = semantics.chooseValue(
582 []const u8,
583 .{
584 "5.9604644775390625e-8",
585 "1.40129846e-45",
586 "4.9406564584124654e-324",
587 "3.64519953188247460253e-4951",
588 "4.94065645841246544176568792868221e-324",
589 "6.47517511943802511092443895822764655e-4966",
590 },
591 );
592 const digits = semantics.chooseValue(i32, .{ 3, 6, 15, 18, 31, 33 });
593 const decimalDigits = semantics.chooseValue(i32, .{ 5, 9, 17, 21, 33, 36 });
594 const epsilon = semantics.chooseValue(
595 []const u8,
596 .{
597 "9.765625e-4",
598 "1.19209290e-7",
599 "2.2204460492503131e-16",
600 "1.08420217248550443401e-19",
601 "4.94065645841246544176568792868221e-324",
602 "1.92592994438723585305597794258492732e-34",
603 },
604 );
605 const mantissaDigits = semantics.chooseValue(i32, .{ 11, 24, 53, 64, 106, 113 });
606
607 const min10Exp = semantics.chooseValue(i32, .{ -4, -37, -307, -4931, -291, -4931 });
608 const max10Exp = semantics.chooseValue(i32, .{ 4, 38, 308, 4932, 308, 4932 });
609
610 const minExp = semantics.chooseValue(i32, .{ -13, -125, -1021, -16381, -968, -16381 });
611 const maxExp = semantics.chooseValue(i32, .{ 16, 128, 1024, 16384, 1024, 16384 });
612
613 const min = semantics.chooseValue(
614 []const u8,
615 .{
616 "6.103515625e-5",
617 "1.17549435e-38",
618 "2.2250738585072014e-308",
619 "3.36210314311209350626e-4932",
620 "2.00416836000897277799610805135016e-292",
621 "3.36210314311209350626267781732175260e-4932",
622 },
623 );
624 const max = semantics.chooseValue(
625 []const u8,
626 .{
627 "6.5504e+4",
628 "3.40282347e+38",
629 "1.7976931348623157e+308",
630 "1.18973149535723176502e+4932",
631 "1.79769313486231580793728971405301e+308",
632 "1.18973149535723176508575932662800702e+4932",
633 },
634 );
635
636 var def_prefix_buf: [32]u8 = undefined;
637 const prefix_slice = std.fmt.bufPrint(&def_prefix_buf, "__{s}_", .{prefix}) catch
638 return error.OutOfMemory;
639
640 try w.print("#define {s}DENORM_MIN__ {s}{s}\n", .{ prefix_slice, denormMin, ext });
641 try w.print("#define {s}HAS_DENORM__\n", .{prefix_slice});
642 try w.print("#define {s}DIG__ {d}\n", .{ prefix_slice, digits });
643 try w.print("#define {s}DECIMAL_DIG__ {d}\n", .{ prefix_slice, decimalDigits });
644
645 try w.print("#define {s}EPSILON__ {s}{s}\n", .{ prefix_slice, epsilon, ext });
646 try w.print("#define {s}HAS_INFINITY__\n", .{prefix_slice});
647 try w.print("#define {s}HAS_QUIET_NAN__\n", .{prefix_slice});
648 try w.print("#define {s}MANT_DIG__ {d}\n", .{ prefix_slice, mantissaDigits });
649
650 try w.print("#define {s}MAX_10_EXP__ {d}\n", .{ prefix_slice, max10Exp });
651 try w.print("#define {s}MAX_EXP__ {d}\n", .{ prefix_slice, maxExp });
652 try w.print("#define {s}MAX__ {s}{s}\n", .{ prefix_slice, max, ext });
653
654 try w.print("#define {s}MIN_10_EXP__ ({d})\n", .{ prefix_slice, min10Exp });
655 try w.print("#define {s}MIN_EXP__ ({d})\n", .{ prefix_slice, minExp });
656 try w.print("#define {s}MIN__ {s}{s}\n", .{ prefix_slice, min, ext });
657}
658
659fn generateTypeMacro(w: anytype, mapper: StrInt.TypeMapper, name: []const u8, ty: Type, langopts: LangOpts) !void {
660 try w.print("#define {s} ", .{name});
661 try ty.print(mapper, langopts, w);
662 try w.writeByte('\n');
663}
664
665fn generateBuiltinTypes(comp: *Compilation) !void {
666 const os = comp.target.os.tag;
667 const wchar: Type = switch (comp.target.cpu.arch) {
668 .xcore => .{ .specifier = .uchar },
669 .ve, .msp430 => .{ .specifier = .uint },
670 .arm, .armeb, .thumb, .thumbeb => .{
671 .specifier = if (os != .windows and os != .netbsd and os != .openbsd) .uint else .int,
672 },
673 .aarch64, .aarch64_be => .{
674 .specifier = if (!os.isDarwin() and os != .netbsd) .uint else .int,
675 },
676 .x86_64, .x86 => .{ .specifier = if (os == .windows) .ushort else .int },
677 else => .{ .specifier = .int },
678 };
679
680 const ptr_width = comp.target.ptrBitWidth();
681 const ptrdiff = if (os == .windows and ptr_width == 64)
682 Type{ .specifier = .long_long }
683 else switch (ptr_width) {
684 16 => Type{ .specifier = .int },
685 32 => Type{ .specifier = .int },
686 64 => Type{ .specifier = .long },
687 else => unreachable,
688 };
689
690 const size = if (os == .windows and ptr_width == 64)
691 Type{ .specifier = .ulong_long }
692 else switch (ptr_width) {
693 16 => Type{ .specifier = .uint },
694 32 => Type{ .specifier = .uint },
695 64 => Type{ .specifier = .ulong },
696 else => unreachable,
697 };
698
699 const va_list = try comp.generateVaListType();
700
701 const pid_t: Type = switch (os) {
702 .haiku => .{ .specifier = .long },
703 // Todo: pid_t is required to "a signed integer type"; are there any systems
704 // on which it is `short int`?
705 else => .{ .specifier = .int },
706 };
707
708 const intmax = target_util.intMaxType(comp.target);
709 const intptr = target_util.intPtrType(comp.target);
710 const int16 = target_util.int16Type(comp.target);
711 const int64 = target_util.int64Type(comp.target);
712
713 comp.types = .{
714 .wchar = wchar,
715 .ptrdiff = ptrdiff,
716 .size = size,
717 .va_list = va_list,
718 .pid_t = pid_t,
719 .intmax = intmax,
720 .intptr = intptr,
721 .int16 = int16,
722 .int64 = int64,
723 .uint_least16_t = comp.intLeastN(16, .unsigned),
724 .uint_least32_t = comp.intLeastN(32, .unsigned),
725 };
726
727 try comp.generateNsConstantStringType();
728}
729
730pub fn float80Type(comp: *const Compilation) ?Type {
731 if (comp.langopts.emulate != .gcc) return null;
732 return target_util.float80Type(comp.target);
733}
734
735/// Smallest integer type with at least N bits
736pub fn intLeastN(comp: *const Compilation, bits: usize, signedness: std.builtin.Signedness) Type {
737 if (bits == 64 and (comp.target.isDarwin() or comp.target.isWasm())) {
738 // WebAssembly and Darwin use `long long` for `int_least64_t` and `int_fast64_t`.
739 return .{ .specifier = if (signedness == .signed) .long_long else .ulong_long };
740 }
741 if (bits == 16 and comp.target.cpu.arch == .avr) {
742 // AVR uses int for int_least16_t and int_fast16_t.
743 return .{ .specifier = if (signedness == .signed) .int else .uint };
744 }
745 const candidates = switch (signedness) {
746 .signed => &[_]Type.Specifier{ .schar, .short, .int, .long, .long_long },
747 .unsigned => &[_]Type.Specifier{ .uchar, .ushort, .uint, .ulong, .ulong_long },
748 };
749 for (candidates) |specifier| {
750 const ty: Type = .{ .specifier = specifier };
751 if (ty.sizeof(comp).? * 8 >= bits) return ty;
752 } else unreachable;
753}
754
755fn intSize(comp: *const Compilation, specifier: Type.Specifier) u64 {
756 const ty = Type{ .specifier = specifier };
757 return ty.sizeof(comp).?;
758}
759
760fn generateFastOrLeastType(
761 comp: *Compilation,
762 bits: usize,
763 kind: enum { least, fast },
764 signedness: std.builtin.Signedness,
765 w: anytype,
766 mapper: StrInt.TypeMapper,
767) !void {
768 const ty = comp.intLeastN(bits, signedness); // defining the fast types as the least types is permitted
769
770 var buf: [32]u8 = undefined;
771 const suffix = "_TYPE__";
772 const base_name = switch (signedness) {
773 .signed => "__INT_",
774 .unsigned => "__UINT_",
775 };
776 const kind_str = switch (kind) {
777 .fast => "FAST",
778 .least => "LEAST",
779 };
780
781 const full = std.fmt.bufPrint(&buf, "{s}{s}{d}{s}", .{
782 base_name, kind_str, bits, suffix,
783 }) catch return error.OutOfMemory;
784
785 try generateTypeMacro(w, mapper, full, ty, comp.langopts);
786
787 const prefix = full[2 .. full.len - suffix.len]; // remove "__" and "_TYPE__"
788
789 switch (signedness) {
790 .signed => try comp.generateIntMaxAndWidth(w, prefix, ty),
791 .unsigned => try comp.generateIntMax(w, prefix, ty),
792 }
793 try comp.generateFmt(prefix, w, ty);
794}
795
796fn generateFastAndLeastWidthTypes(comp: *Compilation, w: anytype, mapper: StrInt.TypeMapper) !void {
797 const sizes = [_]usize{ 8, 16, 32, 64 };
798 for (sizes) |size| {
799 try comp.generateFastOrLeastType(size, .least, .signed, w, mapper);
800 try comp.generateFastOrLeastType(size, .least, .unsigned, w, mapper);
801 try comp.generateFastOrLeastType(size, .fast, .signed, w, mapper);
802 try comp.generateFastOrLeastType(size, .fast, .unsigned, w, mapper);
803 }
804}
805
806fn generateExactWidthTypes(comp: *const Compilation, w: anytype, mapper: StrInt.TypeMapper) !void {
807 try comp.generateExactWidthType(w, mapper, .schar);
808
809 if (comp.intSize(.short) > comp.intSize(.char)) {
810 try comp.generateExactWidthType(w, mapper, .short);
811 }
812
813 if (comp.intSize(.int) > comp.intSize(.short)) {
814 try comp.generateExactWidthType(w, mapper, .int);
815 }
816
817 if (comp.intSize(.long) > comp.intSize(.int)) {
818 try comp.generateExactWidthType(w, mapper, .long);
819 }
820
821 if (comp.intSize(.long_long) > comp.intSize(.long)) {
822 try comp.generateExactWidthType(w, mapper, .long_long);
823 }
824
825 try comp.generateExactWidthType(w, mapper, .uchar);
826 try comp.generateExactWidthIntMax(w, .uchar);
827 try comp.generateExactWidthIntMax(w, .schar);
828
829 if (comp.intSize(.short) > comp.intSize(.char)) {
830 try comp.generateExactWidthType(w, mapper, .ushort);
831 try comp.generateExactWidthIntMax(w, .ushort);
832 try comp.generateExactWidthIntMax(w, .short);
833 }
834
835 if (comp.intSize(.int) > comp.intSize(.short)) {
836 try comp.generateExactWidthType(w, mapper, .uint);
837 try comp.generateExactWidthIntMax(w, .uint);
838 try comp.generateExactWidthIntMax(w, .int);
839 }
840
841 if (comp.intSize(.long) > comp.intSize(.int)) {
842 try comp.generateExactWidthType(w, mapper, .ulong);
843 try comp.generateExactWidthIntMax(w, .ulong);
844 try comp.generateExactWidthIntMax(w, .long);
845 }
846
847 if (comp.intSize(.long_long) > comp.intSize(.long)) {
848 try comp.generateExactWidthType(w, mapper, .ulong_long);
849 try comp.generateExactWidthIntMax(w, .ulong_long);
850 try comp.generateExactWidthIntMax(w, .long_long);
851 }
852}
853
854fn generateFmt(comp: *const Compilation, prefix: []const u8, w: anytype, ty: Type) !void {
855 const unsigned = ty.isUnsignedInt(comp);
856 const modifier = ty.formatModifier();
857 const formats = if (unsigned) "ouxX" else "di";
858 for (formats) |c| {
859 try w.print("#define {s}_FMT{c}__ \"{s}{c}\"\n", .{ prefix, c, modifier, c });
860 }
861}
862
863fn generateSuffixMacro(comp: *const Compilation, prefix: []const u8, w: anytype, ty: Type) !void {
864 return w.print("#define {s}_C_SUFFIX__ {s}\n", .{ prefix, ty.intValueSuffix(comp) });
865}
866
867/// Generate the following for ty:
868/// Name macro (e.g. #define __UINT32_TYPE__ unsigned int)
869/// Format strings (e.g. #define __UINT32_FMTu__ "u")
870/// Suffix macro (e.g. #define __UINT32_C_SUFFIX__ U)
871fn generateExactWidthType(comp: *const Compilation, w: anytype, mapper: StrInt.TypeMapper, specifier: Type.Specifier) !void {
872 var ty = Type{ .specifier = specifier };
873 const width = 8 * ty.sizeof(comp).?;
874 const unsigned = ty.isUnsignedInt(comp);
875
876 if (width == 16) {
877 ty = if (unsigned) comp.types.int16.makeIntegerUnsigned() else comp.types.int16;
878 } else if (width == 64) {
879 ty = if (unsigned) comp.types.int64.makeIntegerUnsigned() else comp.types.int64;
880 }
881
882 var buffer: [16]u8 = undefined;
883 const suffix = "_TYPE__";
884 const full = std.fmt.bufPrint(&buffer, "{s}{d}{s}", .{
885 if (unsigned) "__UINT" else "__INT", width, suffix,
886 }) catch return error.OutOfMemory;
887
888 try generateTypeMacro(w, mapper, full, ty, comp.langopts);
889
890 const prefix = full[0 .. full.len - suffix.len]; // remove "_TYPE__"
891
892 try comp.generateFmt(prefix, w, ty);
893 try comp.generateSuffixMacro(prefix, w, ty);
894}
895
896pub fn hasFloat128(comp: *const Compilation) bool {
897 return target_util.hasFloat128(comp.target);
898}
899
900pub fn hasHalfPrecisionFloatABI(comp: *const Compilation) bool {
901 return comp.langopts.allow_half_args_and_returns or target_util.hasHalfPrecisionFloatABI(comp.target);
902}
903
904fn generateNsConstantStringType(comp: *Compilation) !void {
905 comp.types.ns_constant_string.record = .{
906 .name = try StrInt.intern(comp, "__NSConstantString_tag"),
907 .fields = &comp.types.ns_constant_string.fields,
908 .field_attributes = null,
909 .type_layout = undefined,
910 };
911 const const_int_ptr = Type{ .specifier = .pointer, .data = .{ .sub_type = &comp.types.ns_constant_string.int_ty } };
912 const const_char_ptr = Type{ .specifier = .pointer, .data = .{ .sub_type = &comp.types.ns_constant_string.char_ty } };
913
914 comp.types.ns_constant_string.fields[0] = .{ .name = try StrInt.intern(comp, "isa"), .ty = const_int_ptr };
915 comp.types.ns_constant_string.fields[1] = .{ .name = try StrInt.intern(comp, "flags"), .ty = .{ .specifier = .int } };
916 comp.types.ns_constant_string.fields[2] = .{ .name = try StrInt.intern(comp, "str"), .ty = const_char_ptr };
917 comp.types.ns_constant_string.fields[3] = .{ .name = try StrInt.intern(comp, "length"), .ty = .{ .specifier = .long } };
918 comp.types.ns_constant_string.ty = .{ .specifier = .@"struct", .data = .{ .record = &comp.types.ns_constant_string.record } };
919 record_layout.compute(&comp.types.ns_constant_string.record, comp.types.ns_constant_string.ty, comp, null) catch unreachable;
920}
921
922fn generateVaListType(comp: *Compilation) !Type {
923 const Kind = enum { char_ptr, void_ptr, aarch64_va_list, x86_64_va_list };
924 const kind: Kind = switch (comp.target.cpu.arch) {
925 .aarch64 => switch (comp.target.os.tag) {
926 .windows => @as(Kind, .char_ptr),
927 .ios, .macos, .tvos, .watchos => .char_ptr,
928 else => .aarch64_va_list,
929 },
930 .sparc, .wasm32, .wasm64, .bpfel, .bpfeb, .riscv32, .riscv64, .avr, .spirv32, .spirv64 => .void_ptr,
931 .powerpc => switch (comp.target.os.tag) {
932 .ios, .macos, .tvos, .watchos, .aix => @as(Kind, .char_ptr),
933 else => return Type{ .specifier = .void }, // unknown
934 },
935 .x86, .msp430 => .char_ptr,
936 .x86_64 => switch (comp.target.os.tag) {
937 .windows => @as(Kind, .char_ptr),
938 else => .x86_64_va_list,
939 },
940 else => return Type{ .specifier = .void }, // unknown
941 };
942
943 // TODO this might be bad?
944 const arena = comp.diagnostics.arena.allocator();
945
946 var ty: Type = undefined;
947 switch (kind) {
948 .char_ptr => ty = .{ .specifier = .char },
949 .void_ptr => ty = .{ .specifier = .void },
950 .aarch64_va_list => {
951 const record_ty = try arena.create(Type.Record);
952 record_ty.* = .{
953 .name = try StrInt.intern(comp, "__va_list_tag"),
954 .fields = try arena.alloc(Type.Record.Field, 5),
955 .field_attributes = null,
956 .type_layout = undefined, // computed below
957 };
958 const void_ty = try arena.create(Type);
959 void_ty.* = .{ .specifier = .void };
960 const void_ptr = Type{ .specifier = .pointer, .data = .{ .sub_type = void_ty } };
961 record_ty.fields[0] = .{ .name = try StrInt.intern(comp, "__stack"), .ty = void_ptr };
962 record_ty.fields[1] = .{ .name = try StrInt.intern(comp, "__gr_top"), .ty = void_ptr };
963 record_ty.fields[2] = .{ .name = try StrInt.intern(comp, "__vr_top"), .ty = void_ptr };
964 record_ty.fields[3] = .{ .name = try StrInt.intern(comp, "__gr_offs"), .ty = .{ .specifier = .int } };
965 record_ty.fields[4] = .{ .name = try StrInt.intern(comp, "__vr_offs"), .ty = .{ .specifier = .int } };
966 ty = .{ .specifier = .@"struct", .data = .{ .record = record_ty } };
967 record_layout.compute(record_ty, ty, comp, null) catch unreachable;
968 },
969 .x86_64_va_list => {
970 const record_ty = try arena.create(Type.Record);
971 record_ty.* = .{
972 .name = try StrInt.intern(comp, "__va_list_tag"),
973 .fields = try arena.alloc(Type.Record.Field, 4),
974 .field_attributes = null,
975 .type_layout = undefined, // computed below
976 };
977 const void_ty = try arena.create(Type);
978 void_ty.* = .{ .specifier = .void };
979 const void_ptr = Type{ .specifier = .pointer, .data = .{ .sub_type = void_ty } };
980 record_ty.fields[0] = .{ .name = try StrInt.intern(comp, "gp_offset"), .ty = .{ .specifier = .uint } };
981 record_ty.fields[1] = .{ .name = try StrInt.intern(comp, "fp_offset"), .ty = .{ .specifier = .uint } };
982 record_ty.fields[2] = .{ .name = try StrInt.intern(comp, "overflow_arg_area"), .ty = void_ptr };
983 record_ty.fields[3] = .{ .name = try StrInt.intern(comp, "reg_save_area"), .ty = void_ptr };
984 ty = .{ .specifier = .@"struct", .data = .{ .record = record_ty } };
985 record_layout.compute(record_ty, ty, comp, null) catch unreachable;
986 },
987 }
988 if (kind == .char_ptr or kind == .void_ptr) {
989 const elem_ty = try arena.create(Type);
990 elem_ty.* = ty;
991 ty = Type{ .specifier = .pointer, .data = .{ .sub_type = elem_ty } };
992 } else {
993 const arr_ty = try arena.create(Type.Array);
994 arr_ty.* = .{ .len = 1, .elem = ty };
995 ty = Type{ .specifier = .array, .data = .{ .array = arr_ty } };
996 }
997
998 return ty;
999}
1000
1001fn generateIntMax(comp: *const Compilation, w: anytype, name: []const u8, ty: Type) !void {
1002 const bit_count: u8 = @intCast(ty.sizeof(comp).? * 8);
1003 const unsigned = ty.isUnsignedInt(comp);
1004 const max: u128 = switch (bit_count) {
1005 8 => if (unsigned) std.math.maxInt(u8) else std.math.maxInt(i8),
1006 16 => if (unsigned) std.math.maxInt(u16) else std.math.maxInt(i16),
1007 32 => if (unsigned) std.math.maxInt(u32) else std.math.maxInt(i32),
1008 64 => if (unsigned) std.math.maxInt(u64) else std.math.maxInt(i64),
1009 128 => if (unsigned) std.math.maxInt(u128) else std.math.maxInt(i128),
1010 else => unreachable,
1011 };
1012 try w.print("#define __{s}_MAX__ {d}{s}\n", .{ name, max, ty.intValueSuffix(comp) });
1013}
1014
1015/// Largest value that can be stored in wchar_t
1016pub fn wcharMax(comp: *const Compilation) u32 {
1017 const unsigned = comp.types.wchar.isUnsignedInt(comp);
1018 return switch (comp.types.wchar.bitSizeof(comp).?) {
1019 8 => if (unsigned) std.math.maxInt(u8) else std.math.maxInt(i8),
1020 16 => if (unsigned) std.math.maxInt(u16) else std.math.maxInt(i16),
1021 32 => if (unsigned) std.math.maxInt(u32) else std.math.maxInt(i32),
1022 else => unreachable,
1023 };
1024}
1025
1026fn generateExactWidthIntMax(comp: *const Compilation, w: anytype, specifier: Type.Specifier) !void {
1027 var ty = Type{ .specifier = specifier };
1028 const bit_count: u8 = @intCast(ty.sizeof(comp).? * 8);
1029 const unsigned = ty.isUnsignedInt(comp);
1030
1031 if (bit_count == 64) {
1032 ty = if (unsigned) comp.types.int64.makeIntegerUnsigned() else comp.types.int64;
1033 }
1034
1035 var name_buffer: [6]u8 = undefined;
1036 const name = std.fmt.bufPrint(&name_buffer, "{s}{d}", .{
1037 if (unsigned) "UINT" else "INT", bit_count,
1038 }) catch return error.OutOfMemory;
1039
1040 return comp.generateIntMax(w, name, ty);
1041}
1042
1043fn generateIntWidth(comp: *Compilation, w: anytype, name: []const u8, ty: Type) !void {
1044 try w.print("#define __{s}_WIDTH__ {d}\n", .{ name, 8 * ty.sizeof(comp).? });
1045}
1046
1047fn generateIntMaxAndWidth(comp: *Compilation, w: anytype, name: []const u8, ty: Type) !void {
1048 try comp.generateIntMax(w, name, ty);
1049 try comp.generateIntWidth(w, name, ty);
1050}
1051
1052fn generateSizeofType(comp: *Compilation, w: anytype, name: []const u8, ty: Type) !void {
1053 try w.print("#define {s} {d}\n", .{ name, ty.sizeof(comp).? });
1054}
1055
1056pub fn nextLargestIntSameSign(comp: *const Compilation, ty: Type) ?Type {
1057 assert(ty.isInt());
1058 const specifiers = if (ty.isUnsignedInt(comp))
1059 [_]Type.Specifier{ .short, .int, .long, .long_long }
1060 else
1061 [_]Type.Specifier{ .ushort, .uint, .ulong, .ulong_long };
1062 const size = ty.sizeof(comp).?;
1063 for (specifiers) |specifier| {
1064 const candidate = Type{ .specifier = specifier };
1065 if (candidate.sizeof(comp).? > size) return candidate;
1066 }
1067 return null;
1068}
1069
1070/// Maximum size of an array, in bytes
1071pub fn maxArrayBytes(comp: *const Compilation) u64 {
1072 const max_bits = @min(61, comp.target.ptrBitWidth());
1073 return (@as(u64, 1) << @truncate(max_bits)) - 1;
1074}
1075
1076/// If `enum E { ... }` syntax has a fixed underlying integer type regardless of the presence of
1077/// __attribute__((packed)) or the range of values of the corresponding enumerator constants,
1078/// specify it here.
1079/// TODO: likely incomplete
1080pub fn fixedEnumTagSpecifier(comp: *const Compilation) ?Type.Specifier {
1081 switch (comp.langopts.emulate) {
1082 .msvc => return .int,
1083 .clang => if (comp.target.os.tag == .windows) return .int,
1084 .gcc => {},
1085 }
1086 return null;
1087}
1088
1089pub fn getCharSignedness(comp: *const Compilation) std.builtin.Signedness {
1090 return comp.langopts.char_signedness_override orelse comp.target.charSignedness();
1091}
1092
1093/// Add built-in aro headers directory to system include paths
1094pub fn addBuiltinIncludeDir(comp: *Compilation, aro_dir: []const u8) !void {
1095 var search_path = aro_dir;
1096 while (std.fs.path.dirname(search_path)) |dirname| : (search_path = dirname) {
1097 var base_dir = comp.cwd.openDir(dirname, .{}) catch continue;
1098 defer base_dir.close();
1099
1100 base_dir.access("include/stddef.h", .{}) catch continue;
1101 const path = try std.fs.path.join(comp.gpa, &.{ dirname, "include" });
1102 errdefer comp.gpa.free(path);
1103 try comp.system_include_dirs.append(comp.gpa, path);
1104 break;
1105 } else return error.AroIncludeNotFound;
1106}
1107
1108pub fn addSystemIncludeDir(comp: *Compilation, path: []const u8) !void {
1109 const duped = try comp.gpa.dupe(u8, path);
1110 errdefer comp.gpa.free(duped);
1111 try comp.system_include_dirs.append(comp.gpa, duped);
1112}
1113
1114pub fn getSource(comp: *const Compilation, id: Source.Id) Source {
1115 if (id == .generated) return .{
1116 .path = "<scratch space>",
1117 .buf = comp.generated_buf.items,
1118 .id = .generated,
1119 .splice_locs = &.{},
1120 .kind = .user,
1121 };
1122 return comp.sources.values()[@intFromEnum(id) - 2];
1123}
1124
1125/// Creates a Source from the contents of `reader` and adds it to the Compilation
1126pub fn addSourceFromReader(comp: *Compilation, reader: anytype, path: []const u8, kind: Source.Kind) !Source {
1127 const contents = try reader.readAllAlloc(comp.gpa, std.math.maxInt(u32));
1128 errdefer comp.gpa.free(contents);
1129 return comp.addSourceFromOwnedBuffer(contents, path, kind);
1130}
1131
1132/// Creates a Source from `buf` and adds it to the Compilation
1133/// Performs newline splicing and line-ending normalization to '\n'
1134/// `buf` will be modified and the allocation will be resized if newline splicing
1135/// or line-ending changes happen.
1136/// caller retains ownership of `path`
1137/// To add the contents of an arbitrary reader as a Source, see addSourceFromReader
1138/// To add a file's contents given its path, see addSourceFromPath
1139pub fn addSourceFromOwnedBuffer(comp: *Compilation, buf: []u8, path: []const u8, kind: Source.Kind) !Source {
1140 try comp.sources.ensureUnusedCapacity(comp.gpa, 1);
1141
1142 var contents = buf;
1143 const duped_path = try comp.gpa.dupe(u8, path);
1144 errdefer comp.gpa.free(duped_path);
1145
1146 var splice_list = std.ArrayList(u32).init(comp.gpa);
1147 defer splice_list.deinit();
1148
1149 const source_id: Source.Id = @enumFromInt(comp.sources.count() + 2);
1150
1151 var i: u32 = 0;
1152 var backslash_loc: u32 = undefined;
1153 var state: enum {
1154 beginning_of_file,
1155 bom1,
1156 bom2,
1157 start,
1158 back_slash,
1159 cr,
1160 back_slash_cr,
1161 trailing_ws,
1162 } = .beginning_of_file;
1163 var line: u32 = 1;
1164
1165 for (contents) |byte| {
1166 contents[i] = byte;
1167
1168 switch (byte) {
1169 '\r' => {
1170 switch (state) {
1171 .start, .cr, .beginning_of_file => {
1172 state = .start;
1173 line += 1;
1174 state = .cr;
1175 contents[i] = '\n';
1176 i += 1;
1177 },
1178 .back_slash, .trailing_ws, .back_slash_cr => {
1179 i = backslash_loc;
1180 try splice_list.append(i);
1181 if (state == .trailing_ws) {
1182 try comp.addDiagnostic(.{
1183 .tag = .backslash_newline_escape,
1184 .loc = .{ .id = source_id, .byte_offset = i, .line = line },
1185 }, &.{});
1186 }
1187 state = if (state == .back_slash_cr) .cr else .back_slash_cr;
1188 },
1189 .bom1, .bom2 => break, // invalid utf-8
1190 }
1191 },
1192 '\n' => {
1193 switch (state) {
1194 .start, .beginning_of_file => {
1195 state = .start;
1196 line += 1;
1197 i += 1;
1198 },
1199 .cr, .back_slash_cr => {},
1200 .back_slash, .trailing_ws => {
1201 i = backslash_loc;
1202 if (state == .back_slash or state == .trailing_ws) {
1203 try splice_list.append(i);
1204 }
1205 if (state == .trailing_ws) {
1206 try comp.addDiagnostic(.{
1207 .tag = .backslash_newline_escape,
1208 .loc = .{ .id = source_id, .byte_offset = i, .line = line },
1209 }, &.{});
1210 }
1211 },
1212 .bom1, .bom2 => break,
1213 }
1214 state = .start;
1215 },
1216 '\\' => {
1217 backslash_loc = i;
1218 state = .back_slash;
1219 i += 1;
1220 },
1221 '\t', '\x0B', '\x0C', ' ' => {
1222 switch (state) {
1223 .start, .trailing_ws => {},
1224 .beginning_of_file => state = .start,
1225 .cr, .back_slash_cr => state = .start,
1226 .back_slash => state = .trailing_ws,
1227 .bom1, .bom2 => break,
1228 }
1229 i += 1;
1230 },
1231 '\xEF' => {
1232 i += 1;
1233 state = switch (state) {
1234 .beginning_of_file => .bom1,
1235 else => .start,
1236 };
1237 },
1238 '\xBB' => {
1239 i += 1;
1240 state = switch (state) {
1241 .bom1 => .bom2,
1242 else => .start,
1243 };
1244 },
1245 '\xBF' => {
1246 switch (state) {
1247 .bom2 => i = 0, // rewind and overwrite the BOM
1248 else => i += 1,
1249 }
1250 state = .start;
1251 },
1252 else => {
1253 i += 1;
1254 state = .start;
1255 },
1256 }
1257 }
1258
1259 const splice_locs = try splice_list.toOwnedSlice();
1260 errdefer comp.gpa.free(splice_locs);
1261
1262 if (i != contents.len) contents = try comp.gpa.realloc(contents, i);
1263 errdefer @compileError("errdefers in callers would possibly free the realloced slice using the original len");
1264
1265 const source = Source{
1266 .id = source_id,
1267 .path = duped_path,
1268 .buf = contents,
1269 .splice_locs = splice_locs,
1270 .kind = kind,
1271 };
1272
1273 comp.sources.putAssumeCapacityNoClobber(duped_path, source);
1274 return source;
1275}
1276
1277/// Caller retains ownership of `path` and `buf`.
1278/// Dupes the source buffer; if it is acceptable to modify the source buffer and possibly resize
1279/// the allocation, please use `addSourceFromOwnedBuffer`
1280pub fn addSourceFromBuffer(comp: *Compilation, path: []const u8, buf: []const u8) !Source {
1281 if (comp.sources.get(path)) |some| return some;
1282 if (@as(u64, buf.len) > std.math.maxInt(u32)) return error.StreamTooLong;
1283
1284 const contents = try comp.gpa.dupe(u8, buf);
1285 errdefer comp.gpa.free(contents);
1286
1287 return comp.addSourceFromOwnedBuffer(contents, path, .user);
1288}
1289
1290/// Caller retains ownership of `path`.
1291pub fn addSourceFromPath(comp: *Compilation, path: []const u8) !Source {
1292 return comp.addSourceFromPathExtra(path, .user);
1293}
1294
1295/// Caller retains ownership of `path`.
1296fn addSourceFromPathExtra(comp: *Compilation, path: []const u8, kind: Source.Kind) !Source {
1297 if (comp.sources.get(path)) |some| return some;
1298
1299 if (mem.indexOfScalar(u8, path, 0) != null) {
1300 return error.FileNotFound;
1301 }
1302
1303 const file = try comp.cwd.openFile(path, .{});
1304 defer file.close();
1305
1306 const contents = file.readToEndAlloc(comp.gpa, std.math.maxInt(u32)) catch |err| switch (err) {
1307 error.FileTooBig => return error.StreamTooLong,
1308 else => |e| return e,
1309 };
1310 errdefer comp.gpa.free(contents);
1311
1312 return comp.addSourceFromOwnedBuffer(contents, path, kind);
1313}
1314
1315pub const IncludeDirIterator = struct {
1316 comp: *const Compilation,
1317 cwd_source_id: ?Source.Id,
1318 include_dirs_idx: usize = 0,
1319 sys_include_dirs_idx: usize = 0,
1320 tried_ms_cwd: bool = false,
1321
1322 const FoundSource = struct {
1323 path: []const u8,
1324 kind: Source.Kind,
1325 };
1326
1327 fn next(self: *IncludeDirIterator) ?FoundSource {
1328 if (self.cwd_source_id) |source_id| {
1329 self.cwd_source_id = null;
1330 const path = self.comp.getSource(source_id).path;
1331 return .{ .path = std.fs.path.dirname(path) orelse ".", .kind = .user };
1332 }
1333 if (self.include_dirs_idx < self.comp.include_dirs.items.len) {
1334 defer self.include_dirs_idx += 1;
1335 return .{ .path = self.comp.include_dirs.items[self.include_dirs_idx], .kind = .user };
1336 }
1337 if (self.sys_include_dirs_idx < self.comp.system_include_dirs.items.len) {
1338 defer self.sys_include_dirs_idx += 1;
1339 return .{ .path = self.comp.system_include_dirs.items[self.sys_include_dirs_idx], .kind = .system };
1340 }
1341 if (self.comp.ms_cwd_source_id) |source_id| {
1342 if (self.tried_ms_cwd) return null;
1343 self.tried_ms_cwd = true;
1344 const path = self.comp.getSource(source_id).path;
1345 return .{ .path = std.fs.path.dirname(path) orelse ".", .kind = .user };
1346 }
1347 return null;
1348 }
1349
1350 /// Returned value's path field must be freed by allocator
1351 fn nextWithFile(self: *IncludeDirIterator, filename: []const u8, allocator: Allocator) !?FoundSource {
1352 while (self.next()) |found| {
1353 const path = try std.fs.path.join(allocator, &.{ found.path, filename });
1354 if (self.comp.langopts.ms_extensions) {
1355 std.mem.replaceScalar(u8, path, '\\', '/');
1356 }
1357 return .{ .path = path, .kind = found.kind };
1358 }
1359 return null;
1360 }
1361
1362 /// Advance the iterator until it finds an include directory that matches
1363 /// the directory which contains `source`.
1364 fn skipUntilDirMatch(self: *IncludeDirIterator, source: Source.Id) void {
1365 const path = self.comp.getSource(source).path;
1366 const includer_path = std.fs.path.dirname(path) orelse ".";
1367 while (self.next()) |found| {
1368 if (mem.eql(u8, includer_path, found.path)) break;
1369 }
1370 }
1371};
1372
1373pub fn hasInclude(
1374 comp: *const Compilation,
1375 filename: []const u8,
1376 includer_token_source: Source.Id,
1377 /// angle bracket vs quotes
1378 include_type: IncludeType,
1379 /// __has_include vs __has_include_next
1380 which: WhichInclude,
1381) !bool {
1382 if (mem.indexOfScalar(u8, filename, 0) != null) {
1383 return false;
1384 }
1385
1386 if (std.fs.path.isAbsolute(filename)) {
1387 if (which == .next) return false;
1388 return !std.meta.isError(comp.cwd.access(filename, .{}));
1389 }
1390
1391 const cwd_source_id = switch (include_type) {
1392 .quotes => switch (which) {
1393 .first => includer_token_source,
1394 .next => null,
1395 },
1396 .angle_brackets => null,
1397 };
1398 var it = IncludeDirIterator{ .comp = comp, .cwd_source_id = cwd_source_id };
1399 if (which == .next) {
1400 it.skipUntilDirMatch(includer_token_source);
1401 }
1402
1403 var stack_fallback = std.heap.stackFallback(path_buf_stack_limit, comp.gpa);
1404 const sf_allocator = stack_fallback.get();
1405
1406 while (try it.nextWithFile(filename, sf_allocator)) |found| {
1407 defer sf_allocator.free(found.path);
1408 if (!std.meta.isError(comp.cwd.access(found.path, .{}))) return true;
1409 }
1410 return false;
1411}
1412
1413pub const WhichInclude = enum {
1414 first,
1415 next,
1416};
1417
1418pub const IncludeType = enum {
1419 quotes,
1420 angle_brackets,
1421};
1422
1423fn getFileContents(comp: *Compilation, path: []const u8, limit: ?u32) ![]const u8 {
1424 if (mem.indexOfScalar(u8, path, 0) != null) {
1425 return error.FileNotFound;
1426 }
1427
1428 const file = try comp.cwd.openFile(path, .{});
1429 defer file.close();
1430
1431 var buf = std.ArrayList(u8).init(comp.gpa);
1432 defer buf.deinit();
1433
1434 const max = limit orelse std.math.maxInt(u32);
1435 file.reader().readAllArrayList(&buf, max) catch |e| switch (e) {
1436 error.StreamTooLong => if (limit == null) return e,
1437 else => return e,
1438 };
1439
1440 return buf.toOwnedSlice();
1441}
1442
1443pub fn findEmbed(
1444 comp: *Compilation,
1445 filename: []const u8,
1446 includer_token_source: Source.Id,
1447 /// angle bracket vs quotes
1448 include_type: IncludeType,
1449 limit: ?u32,
1450) !?[]const u8 {
1451 if (std.fs.path.isAbsolute(filename)) {
1452 return if (comp.getFileContents(filename, limit)) |some|
1453 some
1454 else |err| switch (err) {
1455 error.OutOfMemory => |e| return e,
1456 else => null,
1457 };
1458 }
1459
1460 const cwd_source_id = switch (include_type) {
1461 .quotes => includer_token_source,
1462 .angle_brackets => null,
1463 };
1464 var it = IncludeDirIterator{ .comp = comp, .cwd_source_id = cwd_source_id };
1465 var stack_fallback = std.heap.stackFallback(path_buf_stack_limit, comp.gpa);
1466 const sf_allocator = stack_fallback.get();
1467
1468 while (try it.nextWithFile(filename, sf_allocator)) |found| {
1469 defer sf_allocator.free(found.path);
1470 if (comp.getFileContents(found.path, limit)) |some|
1471 return some
1472 else |err| switch (err) {
1473 error.OutOfMemory => return error.OutOfMemory,
1474 else => {},
1475 }
1476 }
1477 return null;
1478}
1479
1480pub fn findInclude(
1481 comp: *Compilation,
1482 filename: []const u8,
1483 includer_token: Token,
1484 /// angle bracket vs quotes
1485 include_type: IncludeType,
1486 /// include vs include_next
1487 which: WhichInclude,
1488) !?Source {
1489 if (std.fs.path.isAbsolute(filename)) {
1490 if (which == .next) return null;
1491 // TODO: classify absolute file as belonging to system includes or not?
1492 return if (comp.addSourceFromPath(filename)) |some|
1493 some
1494 else |err| switch (err) {
1495 error.OutOfMemory => |e| return e,
1496 else => null,
1497 };
1498 }
1499 const cwd_source_id = switch (include_type) {
1500 .quotes => switch (which) {
1501 .first => includer_token.source,
1502 .next => null,
1503 },
1504 .angle_brackets => null,
1505 };
1506 var it = IncludeDirIterator{ .comp = comp, .cwd_source_id = cwd_source_id };
1507
1508 if (which == .next) {
1509 it.skipUntilDirMatch(includer_token.source);
1510 }
1511
1512 var stack_fallback = std.heap.stackFallback(path_buf_stack_limit, comp.gpa);
1513 const sf_allocator = stack_fallback.get();
1514
1515 while (try it.nextWithFile(filename, sf_allocator)) |found| {
1516 defer sf_allocator.free(found.path);
1517 if (comp.addSourceFromPathExtra(found.path, found.kind)) |some| {
1518 if (it.tried_ms_cwd) {
1519 try comp.addDiagnostic(.{
1520 .tag = .ms_search_rule,
1521 .extra = .{ .str = some.path },
1522 .loc = .{
1523 .id = includer_token.source,
1524 .byte_offset = includer_token.start,
1525 .line = includer_token.line,
1526 },
1527 }, &.{});
1528 }
1529 return some;
1530 } else |err| switch (err) {
1531 error.OutOfMemory => return error.OutOfMemory,
1532 else => {},
1533 }
1534 }
1535 return null;
1536}
1537
1538pub fn addPragmaHandler(comp: *Compilation, name: []const u8, handler: *Pragma) Allocator.Error!void {
1539 try comp.pragma_handlers.putNoClobber(comp.gpa, name, handler);
1540}
1541
1542pub fn addDefaultPragmaHandlers(comp: *Compilation) Allocator.Error!void {
1543 const GCC = @import("pragmas/gcc.zig");
1544 var gcc = try GCC.init(comp.gpa);
1545 errdefer gcc.deinit(gcc, comp);
1546
1547 const Once = @import("pragmas/once.zig");
1548 var once = try Once.init(comp.gpa);
1549 errdefer once.deinit(once, comp);
1550
1551 const Message = @import("pragmas/message.zig");
1552 var message = try Message.init(comp.gpa);
1553 errdefer message.deinit(message, comp);
1554
1555 const Pack = @import("pragmas/pack.zig");
1556 var pack = try Pack.init(comp.gpa);
1557 errdefer pack.deinit(pack, comp);
1558
1559 try comp.addPragmaHandler("GCC", gcc);
1560 try comp.addPragmaHandler("once", once);
1561 try comp.addPragmaHandler("message", message);
1562 try comp.addPragmaHandler("pack", pack);
1563}
1564
1565pub fn getPragma(comp: *Compilation, name: []const u8) ?*Pragma {
1566 return comp.pragma_handlers.get(name);
1567}
1568
1569const PragmaEvent = enum {
1570 before_preprocess,
1571 before_parse,
1572 after_parse,
1573};
1574
1575pub fn pragmaEvent(comp: *Compilation, event: PragmaEvent) void {
1576 for (comp.pragma_handlers.values()) |pragma| {
1577 const maybe_func = switch (event) {
1578 .before_preprocess => pragma.beforePreprocess,
1579 .before_parse => pragma.beforeParse,
1580 .after_parse => pragma.afterParse,
1581 };
1582 if (maybe_func) |func| func(pragma, comp);
1583 }
1584}
1585
1586pub fn hasBuiltin(comp: *const Compilation, name: []const u8) bool {
1587 if (std.mem.eql(u8, name, "__builtin_va_arg") or
1588 std.mem.eql(u8, name, "__builtin_choose_expr") or
1589 std.mem.eql(u8, name, "__builtin_bitoffsetof") or
1590 std.mem.eql(u8, name, "__builtin_offsetof") or
1591 std.mem.eql(u8, name, "__builtin_types_compatible_p")) return true;
1592
1593 const builtin = Builtin.fromName(name) orelse return false;
1594 return comp.hasBuiltinFunction(builtin);
1595}
1596
1597pub fn hasBuiltinFunction(comp: *const Compilation, builtin: Builtin) bool {
1598 if (!target_util.builtinEnabled(comp.target, builtin.properties.target_set)) return false;
1599
1600 switch (builtin.properties.language) {
1601 .all_languages => return true,
1602 .all_ms_languages => return comp.langopts.emulate == .msvc,
1603 .gnu_lang, .all_gnu_languages => return comp.langopts.standard.isGNU(),
1604 }
1605}
1606
1607pub fn locSlice(comp: *const Compilation, loc: Source.Location) []const u8 {
1608 var tmp_tokenizer = Tokenizer{
1609 .buf = comp.getSource(loc.id).buf,
1610 .langopts = comp.langopts,
1611 .index = loc.byte_offset,
1612 .source = .generated,
1613 };
1614 const tok = tmp_tokenizer.next();
1615 return tmp_tokenizer.buf[tok.start..tok.end];
1616}
1617
1618pub const CharUnitSize = enum(u32) {
1619 @"1" = 1,
1620 @"2" = 2,
1621 @"4" = 4,
1622
1623 pub fn Type(comptime self: CharUnitSize) type {
1624 return switch (self) {
1625 .@"1" => u8,
1626 .@"2" => u16,
1627 .@"4" => u32,
1628 };
1629 }
1630};
1631
1632pub const addDiagnostic = Diagnostics.add;
1633
1634test "addSourceFromReader" {
1635 const Test = struct {
1636 fn addSourceFromReader(str: []const u8, expected: []const u8, warning_count: u32, splices: []const u32) !void {
1637 var comp = Compilation.init(std.testing.allocator, std.fs.cwd());
1638 defer comp.deinit();
1639
1640 var buf_reader = std.io.fixedBufferStream(str);
1641 const source = try comp.addSourceFromReader(buf_reader.reader(), "path", .user);
1642
1643 try std.testing.expectEqualStrings(expected, source.buf);
1644 try std.testing.expectEqual(warning_count, @as(u32, @intCast(comp.diagnostics.list.items.len)));
1645 try std.testing.expectEqualSlices(u32, splices, source.splice_locs);
1646 }
1647
1648 fn withAllocationFailures(allocator: std.mem.Allocator) !void {
1649 var comp = Compilation.init(allocator, std.fs.cwd());
1650 defer comp.deinit();
1651
1652 _ = try comp.addSourceFromBuffer("path", "spliced\\\nbuffer\n");
1653 _ = try comp.addSourceFromBuffer("path", "non-spliced buffer\n");
1654 }
1655 };
1656 try Test.addSourceFromReader("ab\\\nc", "abc", 0, &.{2});
1657 try Test.addSourceFromReader("ab\\\rc", "abc", 0, &.{2});
1658 try Test.addSourceFromReader("ab\\\r\nc", "abc", 0, &.{2});
1659 try Test.addSourceFromReader("ab\\ \nc", "abc", 1, &.{2});
1660 try Test.addSourceFromReader("ab\\\t\nc", "abc", 1, &.{2});
1661 try Test.addSourceFromReader("ab\\ \t\nc", "abc", 1, &.{2});
1662 try Test.addSourceFromReader("ab\\\r \nc", "ab \nc", 0, &.{2});
1663 try Test.addSourceFromReader("ab\\\\\nc", "ab\\c", 0, &.{3});
1664 try Test.addSourceFromReader("ab\\ \r\nc", "abc", 1, &.{2});
1665 try Test.addSourceFromReader("ab\\ \\\nc", "ab\\ c", 0, &.{4});
1666 try Test.addSourceFromReader("ab\\\r\\\nc", "abc", 0, &.{ 2, 2 });
1667 try Test.addSourceFromReader("ab\\ \rc", "abc", 1, &.{2});
1668 try Test.addSourceFromReader("ab\\", "ab\\", 0, &.{});
1669 try Test.addSourceFromReader("ab\\\\", "ab\\\\", 0, &.{});
1670 try Test.addSourceFromReader("ab\\ ", "ab\\ ", 0, &.{});
1671 try Test.addSourceFromReader("ab\\\n", "ab", 0, &.{2});
1672 try Test.addSourceFromReader("ab\\\r\n", "ab", 0, &.{2});
1673 try Test.addSourceFromReader("ab\\\r", "ab", 0, &.{2});
1674
1675 // carriage return normalization
1676 try Test.addSourceFromReader("ab\r", "ab\n", 0, &.{});
1677 try Test.addSourceFromReader("ab\r\r", "ab\n\n", 0, &.{});
1678 try Test.addSourceFromReader("ab\r\r\n", "ab\n\n", 0, &.{});
1679 try Test.addSourceFromReader("ab\r\r\n\r", "ab\n\n\n", 0, &.{});
1680 try Test.addSourceFromReader("\r\\", "\n\\", 0, &.{});
1681 try Test.addSourceFromReader("\\\r\\", "\\", 0, &.{0});
1682
1683 try std.testing.checkAllAllocationFailures(std.testing.allocator, Test.withAllocationFailures, .{});
1684}
1685
1686test "addSourceFromReader - exhaustive check for carriage return elimination" {
1687 const alphabet = [_]u8{ '\r', '\n', ' ', '\\', 'a' };
1688 const alen = alphabet.len;
1689 var buf: [alphabet.len]u8 = [1]u8{alphabet[0]} ** alen;
1690
1691 var comp = Compilation.init(std.testing.allocator, std.fs.cwd());
1692 defer comp.deinit();
1693
1694 var source_count: u32 = 0;
1695
1696 while (true) {
1697 const source = try comp.addSourceFromBuffer(&buf, &buf);
1698 source_count += 1;
1699 try std.testing.expect(std.mem.indexOfScalar(u8, source.buf, '\r') == null);
1700
1701 if (std.mem.allEqual(u8, &buf, alphabet[alen - 1])) break;
1702
1703 var idx = std.mem.indexOfScalar(u8, &alphabet, buf[buf.len - 1]).?;
1704 buf[buf.len - 1] = alphabet[(idx + 1) % alen];
1705 var j = buf.len - 1;
1706 while (j > 0) : (j -= 1) {
1707 idx = std.mem.indexOfScalar(u8, &alphabet, buf[j - 1]).?;
1708 if (buf[j] == alphabet[0]) buf[j - 1] = alphabet[(idx + 1) % alen] else break;
1709 }
1710 }
1711 try std.testing.expect(source_count == std.math.powi(usize, alen, alen) catch unreachable);
1712}
1713
1714test "ignore BOM at beginning of file" {
1715 const BOM = "\xEF\xBB\xBF";
1716
1717 const Test = struct {
1718 fn run(buf: []const u8) !void {
1719 var comp = Compilation.init(std.testing.allocator, std.fs.cwd());
1720 defer comp.deinit();
1721
1722 var buf_reader = std.io.fixedBufferStream(buf);
1723 const source = try comp.addSourceFromReader(buf_reader.reader(), "file.c", .user);
1724 const expected_output = if (mem.startsWith(u8, buf, BOM)) buf[BOM.len..] else buf;
1725 try std.testing.expectEqualStrings(expected_output, source.buf);
1726 }
1727 };
1728
1729 try Test.run(BOM);
1730 try Test.run(BOM ++ "x");
1731 try Test.run("x" ++ BOM);
1732 try Test.run(BOM ++ " ");
1733 try Test.run(BOM ++ "\n");
1734 try Test.run(BOM ++ "\\");
1735
1736 try Test.run(BOM[0..1] ++ "x");
1737 try Test.run(BOM[0..2] ++ "x");
1738 try Test.run(BOM[1..] ++ "x");
1739 try Test.run(BOM[2..] ++ "x");
1740}
lib/compiler/aro/aro/Diagnostics.zig deleted-602
...@@ -1,602 +0,0 @@
1const std = @import("std");
2const Allocator = mem.Allocator;
3const mem = std.mem;
4const Source = @import("Source.zig");
5const Compilation = @import("Compilation.zig");
6const Attribute = @import("Attribute.zig");
7const Builtins = @import("Builtins.zig");
8const Builtin = Builtins.Builtin;
9const Header = @import("Builtins/Properties.zig").Header;
10const Tree = @import("Tree.zig");
11const is_windows = @import("builtin").os.tag == .windows;
12const LangOpts = @import("LangOpts.zig");
13
14pub const Message = struct {
15 tag: Tag,
16 kind: Kind = undefined,
17 loc: Source.Location = .{},
18 extra: Extra = .{ .none = {} },
19
20 pub const Extra = union {
21 str: []const u8,
22 tok_id: struct {
23 expected: Tree.Token.Id,
24 actual: Tree.Token.Id,
25 },
26 tok_id_expected: Tree.Token.Id,
27 arguments: struct {
28 expected: u32,
29 actual: u32,
30 },
31 codepoints: struct {
32 actual: u21,
33 resembles: u21,
34 },
35 attr_arg_count: struct {
36 attribute: Attribute.Tag,
37 expected: u32,
38 },
39 attr_arg_type: struct {
40 expected: Attribute.ArgumentType,
41 actual: Attribute.ArgumentType,
42 },
43 attr_enum: struct {
44 tag: Attribute.Tag,
45 },
46 ignored_record_attr: struct {
47 tag: Attribute.Tag,
48 specifier: enum { @"struct", @"union", @"enum" },
49 },
50 attribute_todo: struct {
51 tag: Attribute.Tag,
52 kind: enum { variables, fields, types, functions },
53 },
54 builtin_with_header: struct {
55 builtin: Builtin.Tag,
56 header: Header,
57 },
58 invalid_escape: struct {
59 offset: u32,
60 char: u8,
61 },
62 actual_codepoint: u21,
63 ascii: u7,
64 unsigned: u64,
65 offset: u64,
66 pow_2_as_string: u8,
67 signed: i64,
68 normalized: []const u8,
69 none: void,
70 };
71};
72
73const Properties = struct {
74 msg: []const u8,
75 kind: Kind,
76 extra: std.meta.FieldEnum(Message.Extra) = .none,
77 opt: ?u8 = null,
78 all: bool = false,
79 w_extra: bool = false,
80 pedantic: bool = false,
81 suppress_version: ?LangOpts.Standard = null,
82 suppress_unless_version: ?LangOpts.Standard = null,
83 suppress_gnu: bool = false,
84 suppress_gcc: bool = false,
85 suppress_clang: bool = false,
86 suppress_msvc: bool = false,
87
88 pub fn makeOpt(comptime str: []const u8) u16 {
89 return @offsetOf(Options, str);
90 }
91 pub fn getKind(prop: Properties, options: *Options) Kind {
92 const opt = @as([*]Kind, @ptrCast(options))[prop.opt orelse return prop.kind];
93 if (opt == .default) return prop.kind;
94 return opt;
95 }
96 pub const max_bits = Compilation.bit_int_max_bits;
97};
98
99pub const Tag = @import("Diagnostics/messages.zig").with(Properties).Tag;
100
101pub const Kind = enum { @"fatal error", @"error", note, warning, off, default };
102
103pub const Options = struct {
104 // do not directly use these, instead add `const NAME = true;`
105 all: Kind = .default,
106 extra: Kind = .default,
107 pedantic: Kind = .default,
108
109 @"unsupported-pragma": Kind = .default,
110 @"c99-extensions": Kind = .default,
111 @"implicit-int": Kind = .default,
112 @"duplicate-decl-specifier": Kind = .default,
113 @"missing-declaration": Kind = .default,
114 @"extern-initializer": Kind = .default,
115 @"implicit-function-declaration": Kind = .default,
116 @"unused-value": Kind = .default,
117 @"unreachable-code": Kind = .default,
118 @"unknown-warning-option": Kind = .default,
119 @"gnu-empty-struct": Kind = .default,
120 @"gnu-alignof-expression": Kind = .default,
121 @"macro-redefined": Kind = .default,
122 @"generic-qual-type": Kind = .default,
123 multichar: Kind = .default,
124 @"pointer-integer-compare": Kind = .default,
125 @"compare-distinct-pointer-types": Kind = .default,
126 @"literal-conversion": Kind = .default,
127 @"cast-qualifiers": Kind = .default,
128 @"array-bounds": Kind = .default,
129 @"int-conversion": Kind = .default,
130 @"pointer-type-mismatch": Kind = .default,
131 @"c23-extensions": Kind = .default,
132 @"incompatible-pointer-types": Kind = .default,
133 @"excess-initializers": Kind = .default,
134 @"division-by-zero": Kind = .default,
135 @"initializer-overrides": Kind = .default,
136 @"incompatible-pointer-types-discards-qualifiers": Kind = .default,
137 @"unknown-attributes": Kind = .default,
138 @"ignored-attributes": Kind = .default,
139 @"builtin-macro-redefined": Kind = .default,
140 @"gnu-label-as-value": Kind = .default,
141 @"malformed-warning-check": Kind = .default,
142 @"#pragma-messages": Kind = .default,
143 @"newline-eof": Kind = .default,
144 @"empty-translation-unit": Kind = .default,
145 @"implicitly-unsigned-literal": Kind = .default,
146 @"c99-compat": Kind = .default,
147 @"unicode-zero-width": Kind = .default,
148 @"unicode-homoglyph": Kind = .default,
149 unicode: Kind = .default,
150 @"return-type": Kind = .default,
151 @"dollar-in-identifier-extension": Kind = .default,
152 @"unknown-pragmas": Kind = .default,
153 @"predefined-identifier-outside-function": Kind = .default,
154 @"many-braces-around-scalar-init": Kind = .default,
155 uninitialized: Kind = .default,
156 @"gnu-statement-expression": Kind = .default,
157 @"gnu-imaginary-constant": Kind = .default,
158 @"gnu-complex-integer": Kind = .default,
159 @"ignored-qualifiers": Kind = .default,
160 @"integer-overflow": Kind = .default,
161 @"extra-semi": Kind = .default,
162 @"gnu-binary-literal": Kind = .default,
163 @"variadic-macros": Kind = .default,
164 varargs: Kind = .default,
165 @"#warnings": Kind = .default,
166 @"deprecated-declarations": Kind = .default,
167 @"backslash-newline-escape": Kind = .default,
168 @"pointer-to-int-cast": Kind = .default,
169 @"gnu-case-range": Kind = .default,
170 @"c++-compat": Kind = .default,
171 vla: Kind = .default,
172 @"float-overflow-conversion": Kind = .default,
173 @"float-zero-conversion": Kind = .default,
174 @"float-conversion": Kind = .default,
175 @"gnu-folding-constant": Kind = .default,
176 undef: Kind = .default,
177 @"ignored-pragmas": Kind = .default,
178 @"gnu-include-next": Kind = .default,
179 @"include-next-outside-header": Kind = .default,
180 @"include-next-absolute-path": Kind = .default,
181 @"enum-too-large": Kind = .default,
182 @"fixed-enum-extension": Kind = .default,
183 @"designated-init": Kind = .default,
184 @"attribute-warning": Kind = .default,
185 @"invalid-noreturn": Kind = .default,
186 @"zero-length-array": Kind = .default,
187 @"old-style-flexible-struct": Kind = .default,
188 @"gnu-zero-variadic-macro-arguments": Kind = .default,
189 @"main-return-type": Kind = .default,
190 @"expansion-to-defined": Kind = .default,
191 @"bit-int-extension": Kind = .default,
192 @"keyword-macro": Kind = .default,
193 @"pointer-arith": Kind = .default,
194 @"sizeof-array-argument": Kind = .default,
195 @"pre-c23-compat": Kind = .default,
196 @"pointer-bool-conversion": Kind = .default,
197 @"string-conversion": Kind = .default,
198 @"gnu-auto-type": Kind = .default,
199 @"gnu-union-cast": Kind = .default,
200 @"pointer-sign": Kind = .default,
201 @"fuse-ld-path": Kind = .default,
202 @"language-extension-token": Kind = .default,
203 @"complex-component-init": Kind = .default,
204 @"microsoft-include": Kind = .default,
205 @"microsoft-end-of-file": Kind = .default,
206 @"invalid-source-encoding": Kind = .default,
207 @"four-char-constants": Kind = .default,
208 @"unknown-escape-sequence": Kind = .default,
209 @"invalid-pp-token": Kind = .default,
210 @"deprecated-non-prototype": Kind = .default,
211 @"duplicate-embed-param": Kind = .default,
212 @"unsupported-embed-param": Kind = .default,
213 @"unused-result": Kind = .default,
214 normalized: Kind = .default,
215 @"shift-count-negative": Kind = .default,
216 @"shift-count-overflow": Kind = .default,
217 @"constant-conversion": Kind = .default,
218 @"sign-conversion": Kind = .default,
219 nonnull: Kind = .default,
220};
221
222const Diagnostics = @This();
223
224list: std.ArrayListUnmanaged(Message) = .empty,
225arena: std.heap.ArenaAllocator,
226fatal_errors: bool = false,
227options: Options = .{},
228errors: u32 = 0,
229macro_backtrace_limit: u32 = 6,
230
231pub fn warningExists(name: []const u8) bool {
232 inline for (@typeInfo(Options).@"struct".fields) |f| {
233 if (mem.eql(u8, f.name, name)) return true;
234 }
235 return false;
236}
237
238pub fn set(d: *Diagnostics, name: []const u8, to: Kind) !void {
239 inline for (@typeInfo(Options).@"struct".fields) |f| {
240 if (mem.eql(u8, f.name, name)) {
241 @field(d.options, f.name) = to;
242 return;
243 }
244 }
245 try d.addExtra(.{}, .{
246 .tag = .unknown_warning,
247 .extra = .{ .str = name },
248 }, &.{}, true);
249}
250
251pub fn init(gpa: Allocator) Diagnostics {
252 return .{
253 .arena = std.heap.ArenaAllocator.init(gpa),
254 };
255}
256
257pub fn deinit(d: *Diagnostics) void {
258 d.list.deinit(d.arena.child_allocator);
259 d.arena.deinit();
260}
261
262pub fn add(comp: *Compilation, msg: Message, expansion_locs: []const Source.Location) Compilation.Error!void {
263 return comp.diagnostics.addExtra(comp.langopts, msg, expansion_locs, true);
264}
265
266pub fn addExtra(
267 d: *Diagnostics,
268 langopts: LangOpts,
269 msg: Message,
270 expansion_locs: []const Source.Location,
271 note_msg_loc: bool,
272) Compilation.Error!void {
273 const kind = d.tagKind(msg.tag, langopts);
274 if (kind == .off) return;
275 var copy = msg;
276 copy.kind = kind;
277
278 if (expansion_locs.len != 0) copy.loc = expansion_locs[expansion_locs.len - 1];
279 try d.list.append(d.arena.child_allocator, copy);
280 if (expansion_locs.len != 0) {
281 // Add macro backtrace notes in reverse order omitting from the middle if needed.
282 var i = expansion_locs.len - 1;
283 const half = d.macro_backtrace_limit / 2;
284 const limit = if (i < d.macro_backtrace_limit) 0 else i - half;
285 try d.list.ensureUnusedCapacity(
286 d.arena.child_allocator,
287 if (limit == 0) expansion_locs.len else d.macro_backtrace_limit + 1,
288 );
289 while (i > limit) {
290 i -= 1;
291 d.list.appendAssumeCapacity(.{
292 .tag = .expanded_from_here,
293 .kind = .note,
294 .loc = expansion_locs[i],
295 });
296 }
297 if (limit != 0) {
298 d.list.appendAssumeCapacity(.{
299 .tag = .skipping_macro_backtrace,
300 .kind = .note,
301 .extra = .{ .unsigned = expansion_locs.len - d.macro_backtrace_limit },
302 });
303 i = half -| 1;
304 while (i > 0) {
305 i -= 1;
306 d.list.appendAssumeCapacity(.{
307 .tag = .expanded_from_here,
308 .kind = .note,
309 .loc = expansion_locs[i],
310 });
311 }
312 }
313
314 if (note_msg_loc) d.list.appendAssumeCapacity(.{
315 .tag = .expanded_from_here,
316 .kind = .note,
317 .loc = msg.loc,
318 });
319 }
320 if (kind == .@"fatal error" or (kind == .@"error" and d.fatal_errors))
321 return error.FatalError;
322}
323
324pub fn render(comp: *Compilation, config: std.io.tty.Config) void {
325 if (comp.diagnostics.list.items.len == 0) return;
326 var m = defaultMsgWriter(config);
327 defer m.deinit();
328 renderMessages(comp, &m);
329}
330pub fn defaultMsgWriter(config: std.io.tty.Config) MsgWriter {
331 return MsgWriter.init(config);
332}
333
334pub fn renderMessages(comp: *Compilation, m: anytype) void {
335 var errors: u32 = 0;
336 var warnings: u32 = 0;
337 for (comp.diagnostics.list.items) |msg| {
338 switch (msg.kind) {
339 .@"fatal error", .@"error" => errors += 1,
340 .warning => warnings += 1,
341 .note => {},
342 .off => continue, // happens if an error is added before it is disabled
343 .default => unreachable,
344 }
345 renderMessage(comp, m, msg);
346 }
347 const w_s: []const u8 = if (warnings == 1) "" else "s";
348 const e_s: []const u8 = if (errors == 1) "" else "s";
349 if (errors != 0 and warnings != 0) {
350 m.print("{d} warning{s} and {d} error{s} generated.\n", .{ warnings, w_s, errors, e_s });
351 } else if (warnings != 0) {
352 m.print("{d} warning{s} generated.\n", .{ warnings, w_s });
353 } else if (errors != 0) {
354 m.print("{d} error{s} generated.\n", .{ errors, e_s });
355 }
356
357 comp.diagnostics.list.items.len = 0;
358 comp.diagnostics.errors += errors;
359}
360
361pub fn renderMessage(comp: *Compilation, m: anytype, msg: Message) void {
362 var line: ?[]const u8 = null;
363 var end_with_splice = false;
364 const width = if (msg.loc.id != .unused) blk: {
365 var loc = msg.loc;
366 switch (msg.tag) {
367 .escape_sequence_overflow,
368 .invalid_universal_character,
369 => loc.byte_offset += @truncate(msg.extra.offset),
370 .non_standard_escape_char,
371 .unknown_escape_sequence,
372 => loc.byte_offset += msg.extra.invalid_escape.offset,
373 else => {},
374 }
375 const source = comp.getSource(loc.id);
376 var line_col = source.lineCol(loc);
377 line = line_col.line;
378 end_with_splice = line_col.end_with_splice;
379 if (msg.tag == .backslash_newline_escape) {
380 line = line_col.line[0 .. line_col.col - 1];
381 line_col.col += 1;
382 line_col.width += 1;
383 }
384 m.location(source.path, line_col.line_no, line_col.col);
385 break :blk line_col.width;
386 } else 0;
387
388 m.start(msg.kind);
389 const prop = msg.tag.property();
390 switch (prop.extra) {
391 .str => printRt(m, prop.msg, .{"{s}"}, .{msg.extra.str}),
392 .tok_id => printRt(m, prop.msg, .{ "{s}", "{s}" }, .{
393 msg.extra.tok_id.expected.symbol(),
394 msg.extra.tok_id.actual.symbol(),
395 }),
396 .tok_id_expected => printRt(m, prop.msg, .{"{s}"}, .{msg.extra.tok_id_expected.symbol()}),
397 .arguments => printRt(m, prop.msg, .{ "{d}", "{d}" }, .{
398 msg.extra.arguments.expected,
399 msg.extra.arguments.actual,
400 }),
401 .codepoints => printRt(m, prop.msg, .{ "{X:0>4}", "{u}" }, .{
402 msg.extra.codepoints.actual,
403 msg.extra.codepoints.resembles,
404 }),
405 .attr_arg_count => printRt(m, prop.msg, .{ "{s}", "{d}" }, .{
406 @tagName(msg.extra.attr_arg_count.attribute),
407 msg.extra.attr_arg_count.expected,
408 }),
409 .attr_arg_type => printRt(m, prop.msg, .{ "{s}", "{s}" }, .{
410 msg.extra.attr_arg_type.expected.toString(),
411 msg.extra.attr_arg_type.actual.toString(),
412 }),
413 .actual_codepoint => printRt(m, prop.msg, .{"{X:0>4}"}, .{msg.extra.actual_codepoint}),
414 .ascii => printRt(m, prop.msg, .{"{c}"}, .{msg.extra.ascii}),
415 .unsigned => printRt(m, prop.msg, .{"{d}"}, .{msg.extra.unsigned}),
416 .pow_2_as_string => printRt(m, prop.msg, .{"{s}"}, .{switch (msg.extra.pow_2_as_string) {
417 63 => "9223372036854775808",
418 64 => "18446744073709551616",
419 127 => "170141183460469231731687303715884105728",
420 128 => "340282366920938463463374607431768211456",
421 else => unreachable,
422 }}),
423 .signed => printRt(m, prop.msg, .{"{d}"}, .{msg.extra.signed}),
424 .attr_enum => printRt(m, prop.msg, .{ "{s}", "{s}" }, .{
425 @tagName(msg.extra.attr_enum.tag),
426 Attribute.Formatting.choices(msg.extra.attr_enum.tag),
427 }),
428 .ignored_record_attr => printRt(m, prop.msg, .{ "{s}", "{s}" }, .{
429 @tagName(msg.extra.ignored_record_attr.tag),
430 @tagName(msg.extra.ignored_record_attr.specifier),
431 }),
432 .attribute_todo => printRt(m, prop.msg, .{ "{s}", "{s}" }, .{
433 @tagName(msg.extra.attribute_todo.tag),
434 @tagName(msg.extra.attribute_todo.kind),
435 }),
436 .builtin_with_header => printRt(m, prop.msg, .{ "{s}", "{s}" }, .{
437 @tagName(msg.extra.builtin_with_header.header),
438 Builtin.nameFromTag(msg.extra.builtin_with_header.builtin).span(),
439 }),
440 .invalid_escape => {
441 if (std.ascii.isPrint(msg.extra.invalid_escape.char)) {
442 const str: [1]u8 = .{msg.extra.invalid_escape.char};
443 printRt(m, prop.msg, .{"{s}"}, .{&str});
444 } else {
445 var buf: [3]u8 = undefined;
446 const str = std.fmt.bufPrint(&buf, "x{x}", .{std.fmt.fmtSliceHexLower(&.{msg.extra.invalid_escape.char})}) catch unreachable;
447 printRt(m, prop.msg, .{"{s}"}, .{str});
448 }
449 },
450 .normalized => {
451 const f = struct {
452 pub fn f(
453 bytes: []const u8,
454 comptime _: []const u8,
455 _: std.fmt.FormatOptions,
456 writer: anytype,
457 ) !void {
458 var it: std.unicode.Utf8Iterator = .{
459 .bytes = bytes,
460 .i = 0,
461 };
462 while (it.nextCodepoint()) |codepoint| {
463 if (codepoint < 0x7F) {
464 try writer.writeByte(@intCast(codepoint));
465 } else if (codepoint < 0xFFFF) {
466 try writer.writeAll("\\u");
467 try std.fmt.formatInt(codepoint, 16, .upper, .{
468 .fill = '0',
469 .width = 4,
470 }, writer);
471 } else {
472 try writer.writeAll("\\U");
473 try std.fmt.formatInt(codepoint, 16, .upper, .{
474 .fill = '0',
475 .width = 8,
476 }, writer);
477 }
478 }
479 }
480 }.f;
481 printRt(m, prop.msg, .{"{s}"}, .{
482 std.fmt.Formatter(f){ .data = msg.extra.normalized },
483 });
484 },
485 .none, .offset => m.write(prop.msg),
486 }
487
488 if (prop.opt) |some| {
489 if (msg.kind == .@"error" and prop.kind != .@"error") {
490 m.print(" [-Werror,-W{s}]", .{optName(some)});
491 } else if (msg.kind != .note) {
492 m.print(" [-W{s}]", .{optName(some)});
493 }
494 }
495
496 m.end(line, width, end_with_splice);
497}
498
499fn printRt(m: anytype, str: []const u8, comptime fmts: anytype, args: anytype) void {
500 var i: usize = 0;
501 inline for (fmts, args) |fmt, arg| {
502 const new = std.mem.indexOfPos(u8, str, i, fmt).?;
503 m.write(str[i..new]);
504 i = new + fmt.len;
505 m.print(fmt, .{arg});
506 }
507 m.write(str[i..]);
508}
509
510fn optName(offset: u16) []const u8 {
511 return std.meta.fieldNames(Options)[offset / @sizeOf(Kind)];
512}
513
514fn tagKind(d: *Diagnostics, tag: Tag, langopts: LangOpts) Kind {
515 const prop = tag.property();
516 var kind = prop.getKind(&d.options);
517
518 if (prop.all) {
519 if (d.options.all != .default) kind = d.options.all;
520 }
521 if (prop.w_extra) {
522 if (d.options.extra != .default) kind = d.options.extra;
523 }
524 if (prop.pedantic) {
525 if (d.options.pedantic != .default) kind = d.options.pedantic;
526 }
527 if (prop.suppress_version) |some| if (langopts.standard.atLeast(some)) return .off;
528 if (prop.suppress_unless_version) |some| if (!langopts.standard.atLeast(some)) return .off;
529 if (prop.suppress_gnu and langopts.standard.isExplicitGNU()) return .off;
530 if (prop.suppress_gcc and langopts.emulate == .gcc) return .off;
531 if (prop.suppress_clang and langopts.emulate == .clang) return .off;
532 if (prop.suppress_msvc and langopts.emulate == .msvc) return .off;
533 if (kind == .@"error" and d.fatal_errors) kind = .@"fatal error";
534 return kind;
535}
536
537const MsgWriter = struct {
538 w: std.io.BufferedWriter(4096, std.fs.File.Writer),
539 config: std.io.tty.Config,
540
541 fn init(config: std.io.tty.Config) MsgWriter {
542 std.debug.lockStdErr();
543 return .{
544 .w = std.io.bufferedWriter(std.io.getStdErr().writer()),
545 .config = config,
546 };
547 }
548
549 pub fn deinit(m: *MsgWriter) void {
550 m.w.flush() catch {};
551 std.debug.unlockStdErr();
552 }
553
554 pub fn print(m: *MsgWriter, comptime fmt: []const u8, args: anytype) void {
555 m.w.writer().print(fmt, args) catch {};
556 }
557
558 fn write(m: *MsgWriter, msg: []const u8) void {
559 m.w.writer().writeAll(msg) catch {};
560 }
561
562 fn setColor(m: *MsgWriter, color: std.io.tty.Color) void {
563 m.config.setColor(m.w.writer(), color) catch {};
564 }
565
566 fn location(m: *MsgWriter, path: []const u8, line: u32, col: u32) void {
567 m.setColor(.bold);
568 m.print("{s}:{d}:{d}: ", .{ path, line, col });
569 }
570
571 fn start(m: *MsgWriter, kind: Kind) void {
572 switch (kind) {
573 .@"fatal error", .@"error" => m.setColor(.bright_red),
574 .note => m.setColor(.bright_cyan),
575 .warning => m.setColor(.bright_magenta),
576 .off, .default => unreachable,
577 }
578 m.write(switch (kind) {
579 .@"fatal error" => "fatal error: ",
580 .@"error" => "error: ",
581 .note => "note: ",
582 .warning => "warning: ",
583 .off, .default => unreachable,
584 });
585 m.setColor(.white);
586 }
587
588 fn end(m: *MsgWriter, maybe_line: ?[]const u8, col: u32, end_with_splice: bool) void {
589 const line = maybe_line orelse {
590 m.write("\n");
591 m.setColor(.reset);
592 return;
593 };
594 const trailer = if (end_with_splice) "\\ " else "";
595 m.setColor(.reset);
596 m.print("\n{s}{s}\n{s: >[3]}", .{ line, trailer, "", col });
597 m.setColor(.bold);
598 m.setColor(.bright_green);
599 m.write("^\n");
600 m.setColor(.reset);
601 }
602};
lib/compiler/aro/aro/Diagnostics/messages.zig deleted-1041
...@@ -1,1041 +0,0 @@
1//! Autogenerated by GenerateDef from src/aro/Diagnostics/messages.def, do not edit
2// zig fmt: off
3
4const std = @import("std");
5
6pub fn with(comptime Properties: type) type {
7return struct {
8const W = Properties.makeOpt;
9const pointer_sign_message = " converts between pointers to integer types with different sign";
10const expected_arguments = "expected {d} argument(s) got {d}";
11pub const Tag = enum {
12 todo,
13 error_directive,
14 warning_directive,
15 elif_without_if,
16 elif_after_else,
17 elifdef_without_if,
18 elifdef_after_else,
19 elifndef_without_if,
20 elifndef_after_else,
21 else_without_if,
22 else_after_else,
23 endif_without_if,
24 unknown_pragma,
25 line_simple_digit,
26 line_invalid_filename,
27 unterminated_conditional_directive,
28 invalid_preprocessing_directive,
29 macro_name_missing,
30 extra_tokens_directive_end,
31 expected_value_in_expr,
32 closing_paren,
33 to_match_paren,
34 to_match_brace,
35 to_match_bracket,
36 header_str_closing,
37 header_str_match,
38 string_literal_in_pp_expr,
39 float_literal_in_pp_expr,
40 defined_as_macro_name,
41 macro_name_must_be_identifier,
42 whitespace_after_macro_name,
43 hash_hash_at_start,
44 hash_hash_at_end,
45 pasting_formed_invalid,
46 missing_paren_param_list,
47 unterminated_macro_param_list,
48 invalid_token_param_list,
49 expected_comma_param_list,
50 hash_not_followed_param,
51 expected_filename,
52 empty_filename,
53 expected_invalid,
54 expected_eof,
55 expected_token,
56 expected_expr,
57 expected_integer_constant_expr,
58 missing_type_specifier,
59 missing_type_specifier_c23,
60 multiple_storage_class,
61 static_assert_failure,
62 static_assert_failure_message,
63 expected_type,
64 cannot_combine_spec,
65 duplicate_decl_spec,
66 restrict_non_pointer,
67 expected_external_decl,
68 expected_ident_or_l_paren,
69 missing_declaration,
70 func_not_in_root,
71 illegal_initializer,
72 extern_initializer,
73 spec_from_typedef,
74 param_before_var_args,
75 void_only_param,
76 void_param_qualified,
77 void_must_be_first_param,
78 invalid_storage_on_param,
79 threadlocal_non_var,
80 func_spec_non_func,
81 illegal_storage_on_func,
82 illegal_storage_on_global,
83 expected_stmt,
84 func_cannot_return_func,
85 func_cannot_return_array,
86 undeclared_identifier,
87 not_callable,
88 unsupported_str_cat,
89 static_func_not_global,
90 implicit_func_decl,
91 unknown_builtin,
92 implicit_builtin,
93 implicit_builtin_header_note,
94 expected_param_decl,
95 invalid_old_style_params,
96 expected_fn_body,
97 invalid_void_param,
98 unused_value,
99 continue_not_in_loop,
100 break_not_in_loop_or_switch,
101 unreachable_code,
102 duplicate_label,
103 previous_label,
104 undeclared_label,
105 case_not_in_switch,
106 duplicate_switch_case,
107 multiple_default,
108 previous_case,
109 expected_arguments,
110 callee_with_static_array,
111 array_argument_too_small,
112 non_null_argument,
113 expected_arguments_old,
114 expected_at_least_arguments,
115 invalid_static_star,
116 static_non_param,
117 array_qualifiers,
118 star_non_param,
119 variable_len_array_file_scope,
120 useless_static,
121 negative_array_size,
122 array_incomplete_elem,
123 array_func_elem,
124 static_non_outermost_array,
125 qualifier_non_outermost_array,
126 unterminated_macro_arg_list,
127 unknown_warning,
128 overflow,
129 int_literal_too_big,
130 indirection_ptr,
131 addr_of_rvalue,
132 addr_of_bitfield,
133 not_assignable,
134 ident_or_l_brace,
135 empty_enum,
136 redefinition,
137 previous_definition,
138 expected_identifier,
139 expected_str_literal,
140 expected_str_literal_in,
141 parameter_missing,
142 empty_record,
143 empty_record_size,
144 wrong_tag,
145 expected_parens_around_typename,
146 alignof_expr,
147 invalid_alignof,
148 invalid_sizeof,
149 macro_redefined,
150 generic_qual_type,
151 generic_array_type,
152 generic_func_type,
153 generic_duplicate,
154 generic_duplicate_here,
155 generic_duplicate_default,
156 generic_no_match,
157 escape_sequence_overflow,
158 invalid_universal_character,
159 incomplete_universal_character,
160 multichar_literal_warning,
161 invalid_multichar_literal,
162 wide_multichar_literal,
163 char_lit_too_wide,
164 char_too_large,
165 must_use_struct,
166 must_use_union,
167 must_use_enum,
168 redefinition_different_sym,
169 redefinition_incompatible,
170 redefinition_of_parameter,
171 invalid_bin_types,
172 comparison_ptr_int,
173 comparison_distinct_ptr,
174 incompatible_pointers,
175 invalid_argument_un,
176 incompatible_assign,
177 implicit_ptr_to_int,
178 invalid_cast_to_float,
179 invalid_cast_to_pointer,
180 invalid_cast_type,
181 qual_cast,
182 invalid_index,
183 invalid_subscript,
184 array_after,
185 array_before,
186 statement_int,
187 statement_scalar,
188 func_should_return,
189 incompatible_return,
190 incompatible_return_sign,
191 implicit_int_to_ptr,
192 func_does_not_return,
193 void_func_returns_value,
194 incompatible_arg,
195 incompatible_ptr_arg,
196 incompatible_ptr_arg_sign,
197 parameter_here,
198 atomic_array,
199 atomic_func,
200 atomic_incomplete,
201 addr_of_register,
202 variable_incomplete_ty,
203 parameter_incomplete_ty,
204 tentative_array,
205 deref_incomplete_ty_ptr,
206 alignas_on_func,
207 alignas_on_param,
208 minimum_alignment,
209 maximum_alignment,
210 negative_alignment,
211 align_ignored,
212 zero_align_ignored,
213 non_pow2_align,
214 pointer_mismatch,
215 static_assert_not_constant,
216 static_assert_missing_message,
217 pre_c23_compat,
218 unbound_vla,
219 array_too_large,
220 record_too_large,
221 incompatible_ptr_init,
222 incompatible_ptr_init_sign,
223 incompatible_ptr_assign,
224 incompatible_ptr_assign_sign,
225 vla_init,
226 func_init,
227 incompatible_init,
228 empty_scalar_init,
229 excess_scalar_init,
230 excess_str_init,
231 excess_struct_init,
232 excess_array_init,
233 str_init_too_long,
234 arr_init_too_long,
235 invalid_typeof,
236 division_by_zero,
237 division_by_zero_macro,
238 builtin_choose_cond,
239 alignas_unavailable,
240 case_val_unavailable,
241 enum_val_unavailable,
242 incompatible_array_init,
243 array_init_str,
244 initializer_overrides,
245 previous_initializer,
246 invalid_array_designator,
247 negative_array_designator,
248 oob_array_designator,
249 invalid_field_designator,
250 no_such_field_designator,
251 empty_aggregate_init_braces,
252 ptr_init_discards_quals,
253 ptr_assign_discards_quals,
254 ptr_ret_discards_quals,
255 ptr_arg_discards_quals,
256 unknown_attribute,
257 ignored_attribute,
258 invalid_fallthrough,
259 cannot_apply_attribute_to_statement,
260 builtin_macro_redefined,
261 feature_check_requires_identifier,
262 missing_tok_builtin,
263 gnu_label_as_value,
264 expected_record_ty,
265 member_expr_not_ptr,
266 member_expr_ptr,
267 no_such_member,
268 malformed_warning_check,
269 invalid_computed_goto,
270 pragma_warning_message,
271 pragma_error_message,
272 pragma_message,
273 pragma_requires_string_literal,
274 poisoned_identifier,
275 pragma_poison_identifier,
276 pragma_poison_macro,
277 newline_eof,
278 empty_translation_unit,
279 omitting_parameter_name,
280 non_int_bitfield,
281 negative_bitwidth,
282 zero_width_named_field,
283 bitfield_too_big,
284 invalid_utf8,
285 implicitly_unsigned_literal,
286 invalid_preproc_operator,
287 invalid_preproc_expr_start,
288 c99_compat,
289 unexpected_character,
290 invalid_identifier_start_char,
291 unicode_zero_width,
292 unicode_homoglyph,
293 meaningless_asm_qual,
294 duplicate_asm_qual,
295 invalid_asm_str,
296 dollar_in_identifier_extension,
297 dollars_in_identifiers,
298 expanded_from_here,
299 skipping_macro_backtrace,
300 pragma_operator_string_literal,
301 unknown_gcc_pragma,
302 unknown_gcc_pragma_directive,
303 predefined_top_level,
304 incompatible_va_arg,
305 too_many_scalar_init_braces,
306 uninitialized_in_own_init,
307 gnu_statement_expression,
308 stmt_expr_not_allowed_file_scope,
309 gnu_imaginary_constant,
310 plain_complex,
311 complex_int,
312 qual_on_ret_type,
313 cli_invalid_standard,
314 cli_invalid_target,
315 cli_invalid_emulate,
316 cli_unknown_arg,
317 cli_error,
318 cli_unused_link_object,
319 cli_unknown_linker,
320 extra_semi,
321 func_field,
322 vla_field,
323 field_incomplete_ty,
324 flexible_in_union,
325 flexible_non_final,
326 flexible_in_empty,
327 duplicate_member,
328 binary_integer_literal,
329 gnu_va_macro,
330 builtin_must_be_called,
331 va_start_not_in_func,
332 va_start_fixed_args,
333 va_start_not_last_param,
334 attribute_not_enough_args,
335 attribute_too_many_args,
336 attribute_arg_invalid,
337 unknown_attr_enum,
338 attribute_requires_identifier,
339 declspec_not_enabled,
340 declspec_attr_not_supported,
341 deprecated_declarations,
342 deprecated_note,
343 unavailable,
344 unavailable_note,
345 warning_attribute,
346 error_attribute,
347 ignored_record_attr,
348 backslash_newline_escape,
349 array_size_non_int,
350 cast_to_smaller_int,
351 gnu_switch_range,
352 empty_case_range,
353 non_standard_escape_char,
354 invalid_pp_stringify_escape,
355 vla,
356 int_value_changed,
357 sign_conversion,
358 float_overflow_conversion,
359 float_out_of_range,
360 float_zero_conversion,
361 float_value_changed,
362 float_to_int,
363 const_decl_folded,
364 const_decl_folded_vla,
365 redefinition_of_typedef,
366 undefined_macro,
367 fn_macro_undefined,
368 preprocessing_directive_only,
369 missing_lparen_after_builtin,
370 offsetof_ty,
371 offsetof_incomplete,
372 offsetof_array,
373 pragma_pack_lparen,
374 pragma_pack_rparen,
375 pragma_pack_unknown_action,
376 pragma_pack_show,
377 pragma_pack_int,
378 pragma_pack_int_ident,
379 pragma_pack_undefined_pop,
380 pragma_pack_empty_stack,
381 cond_expr_type,
382 too_many_includes,
383 enumerator_too_small,
384 enumerator_too_large,
385 include_next,
386 include_next_outside_header,
387 enumerator_overflow,
388 enum_not_representable,
389 enum_too_large,
390 enum_fixed,
391 enum_prev_nonfixed,
392 enum_prev_fixed,
393 enum_different_explicit_ty,
394 enum_not_representable_fixed,
395 transparent_union_wrong_type,
396 transparent_union_one_field,
397 transparent_union_size,
398 transparent_union_size_note,
399 designated_init_invalid,
400 designated_init_needed,
401 ignore_common,
402 ignore_nocommon,
403 non_string_ignored,
404 local_variable_attribute,
405 ignore_cold,
406 ignore_hot,
407 ignore_noinline,
408 ignore_always_inline,
409 invalid_noreturn,
410 nodiscard_unused,
411 warn_unused_result,
412 invalid_vec_elem_ty,
413 vec_size_not_multiple,
414 invalid_imag,
415 invalid_real,
416 zero_length_array,
417 old_style_flexible_struct,
418 comma_deletion_va_args,
419 main_return_type,
420 expansion_to_defined,
421 invalid_int_suffix,
422 invalid_float_suffix,
423 invalid_octal_digit,
424 invalid_binary_digit,
425 exponent_has_no_digits,
426 hex_floating_constant_requires_exponent,
427 sizeof_returns_zero,
428 declspec_not_allowed_after_declarator,
429 declarator_name_tok,
430 type_not_supported_on_target,
431 bit_int,
432 unsigned_bit_int_too_small,
433 signed_bit_int_too_small,
434 unsigned_bit_int_too_big,
435 signed_bit_int_too_big,
436 keyword_macro,
437 ptr_arithmetic_incomplete,
438 callconv_not_supported,
439 pointer_arith_void,
440 sizeof_array_arg,
441 array_address_to_bool,
442 string_literal_to_bool,
443 constant_expression_conversion_not_allowed,
444 invalid_object_cast,
445 cli_invalid_fp_eval_method,
446 suggest_pointer_for_invalid_fp16,
447 bitint_suffix,
448 auto_type_extension,
449 auto_type_not_allowed,
450 auto_type_requires_initializer,
451 auto_type_requires_single_declarator,
452 auto_type_requires_plain_declarator,
453 invalid_cast_to_auto_type,
454 auto_type_from_bitfield,
455 array_of_auto_type,
456 auto_type_with_init_list,
457 missing_semicolon,
458 tentative_definition_incomplete,
459 forward_declaration_here,
460 gnu_union_cast,
461 invalid_union_cast,
462 cast_to_incomplete_type,
463 invalid_source_epoch,
464 fuse_ld_path,
465 invalid_rtlib,
466 unsupported_rtlib_gcc,
467 invalid_unwindlib,
468 incompatible_unwindlib,
469 gnu_asm_disabled,
470 extension_token_used,
471 complex_component_init,
472 complex_prefix_postfix_op,
473 not_floating_type,
474 argument_types_differ,
475 ms_search_rule,
476 ctrl_z_eof,
477 illegal_char_encoding_warning,
478 illegal_char_encoding_error,
479 ucn_basic_char_error,
480 ucn_basic_char_warning,
481 ucn_control_char_error,
482 ucn_control_char_warning,
483 c89_ucn_in_literal,
484 four_char_char_literal,
485 multi_char_char_literal,
486 missing_hex_escape,
487 unknown_escape_sequence,
488 attribute_requires_string,
489 unterminated_string_literal_warning,
490 unterminated_string_literal_error,
491 empty_char_literal_warning,
492 empty_char_literal_error,
493 unterminated_char_literal_warning,
494 unterminated_char_literal_error,
495 unterminated_comment,
496 def_no_proto_deprecated,
497 passing_args_to_kr,
498 unknown_type_name,
499 label_compound_end,
500 u8_char_lit,
501 malformed_embed_param,
502 malformed_embed_limit,
503 duplicate_embed_param,
504 unsupported_embed_param,
505 invalid_compound_literal_storage_class,
506 va_opt_lparen,
507 va_opt_rparen,
508 attribute_int_out_of_range,
509 identifier_not_normalized,
510 c23_auto_plain_declarator,
511 c23_auto_single_declarator,
512 c32_auto_requires_initializer,
513 c23_auto_scalar_init,
514 negative_shift_count,
515 too_big_shift_count,
516 complex_conj,
517 overflow_builtin_requires_int,
518 overflow_result_requires_ptr,
519 attribute_todo,
520 invalid_type_underlying_enum,
521 auto_type_self_initialized,
522
523 pub fn property(tag: Tag) Properties {
524 return named_data[@intFromEnum(tag)];
525 }
526
527 const named_data = [_]Properties{
528 .{ .msg = "TODO: {s}", .extra = .str, .kind = .@"error" },
529 .{ .msg = "{s}", .extra = .str, .kind = .@"error" },
530 .{ .msg = "{s}", .opt = W("#warnings"), .extra = .str, .kind = .warning },
531 .{ .msg = "#elif without #if", .kind = .@"error" },
532 .{ .msg = "#elif after #else", .kind = .@"error" },
533 .{ .msg = "#elifdef without #if", .kind = .@"error" },
534 .{ .msg = "#elifdef after #else", .kind = .@"error" },
535 .{ .msg = "#elifndef without #if", .kind = .@"error" },
536 .{ .msg = "#elifndef after #else", .kind = .@"error" },
537 .{ .msg = "#else without #if", .kind = .@"error" },
538 .{ .msg = "#else after #else", .kind = .@"error" },
539 .{ .msg = "#endif without #if", .kind = .@"error" },
540 .{ .msg = "unknown pragma ignored", .opt = W("unknown-pragmas"), .kind = .off, .all = true },
541 .{ .msg = "#line directive requires a simple digit sequence", .kind = .@"error" },
542 .{ .msg = "invalid filename for #line directive", .kind = .@"error" },
543 .{ .msg = "unterminated conditional directive", .kind = .@"error" },
544 .{ .msg = "invalid preprocessing directive", .kind = .@"error" },
545 .{ .msg = "macro name missing", .kind = .@"error" },
546 .{ .msg = "extra tokens at end of macro directive", .kind = .@"error" },
547 .{ .msg = "expected value in expression", .kind = .@"error" },
548 .{ .msg = "expected closing ')'", .kind = .@"error" },
549 .{ .msg = "to match this '('", .kind = .note },
550 .{ .msg = "to match this '{'", .kind = .note },
551 .{ .msg = "to match this '['", .kind = .note },
552 .{ .msg = "expected closing '>'", .kind = .@"error" },
553 .{ .msg = "to match this '<'", .kind = .note },
554 .{ .msg = "string literal in preprocessor expression", .kind = .@"error" },
555 .{ .msg = "floating point literal in preprocessor expression", .kind = .@"error" },
556 .{ .msg = "'defined' cannot be used as a macro name", .kind = .@"error" },
557 .{ .msg = "macro name must be an identifier", .kind = .@"error" },
558 .{ .msg = "ISO C99 requires whitespace after the macro name", .opt = W("c99-extensions"), .kind = .warning },
559 .{ .msg = "'##' cannot appear at the start of a macro expansion", .kind = .@"error" },
560 .{ .msg = "'##' cannot appear at the end of a macro expansion", .kind = .@"error" },
561 .{ .msg = "pasting formed '{s}', an invalid preprocessing token", .extra = .str, .kind = .@"error" },
562 .{ .msg = "missing ')' in macro parameter list", .kind = .@"error" },
563 .{ .msg = "unterminated macro param list", .kind = .@"error" },
564 .{ .msg = "invalid token in macro parameter list", .kind = .@"error" },
565 .{ .msg = "expected comma in macro parameter list", .kind = .@"error" },
566 .{ .msg = "'#' is not followed by a macro parameter", .kind = .@"error" },
567 .{ .msg = "expected \"FILENAME\" or <FILENAME>", .kind = .@"error" },
568 .{ .msg = "empty filename", .kind = .@"error" },
569 .{ .msg = "expected '{s}', found invalid bytes", .extra = .tok_id_expected, .kind = .@"error" },
570 .{ .msg = "expected '{s}' before end of file", .extra = .tok_id_expected, .kind = .@"error" },
571 .{ .msg = "expected '{s}', found '{s}'", .extra = .tok_id, .kind = .@"error" },
572 .{ .msg = "expected expression", .kind = .@"error" },
573 .{ .msg = "expression is not an integer constant expression", .kind = .@"error" },
574 .{ .msg = "type specifier missing, defaults to 'int'", .opt = W("implicit-int"), .kind = .warning, .all = true },
575 .{ .msg = "a type specifier is required for all declarations", .kind = .@"error" },
576 .{ .msg = "cannot combine with previous '{s}' declaration specifier", .extra = .str, .kind = .@"error" },
577 .{ .msg = "static assertion failed", .kind = .@"error" },
578 .{ .msg = "static assertion failed {s}", .extra = .str, .kind = .@"error" },
579 .{ .msg = "expected a type", .kind = .@"error" },
580 .{ .msg = "cannot combine with previous '{s}' specifier", .extra = .str, .kind = .@"error" },
581 .{ .msg = "duplicate '{s}' declaration specifier", .extra = .str, .opt = W("duplicate-decl-specifier"), .kind = .warning, .all = true },
582 .{ .msg = "restrict requires a pointer or reference ('{s}' is invalid)", .extra = .str, .kind = .@"error" },
583 .{ .msg = "expected external declaration", .kind = .@"error" },
584 .{ .msg = "expected identifier or '('", .kind = .@"error" },
585 .{ .msg = "declaration does not declare anything", .opt = W("missing-declaration"), .kind = .warning },
586 .{ .msg = "function definition is not allowed here", .kind = .@"error" },
587 .{ .msg = "illegal initializer (only variables can be initialized)", .kind = .@"error" },
588 .{ .msg = "extern variable has initializer", .opt = W("extern-initializer"), .kind = .warning },
589 .{ .msg = "'{s}' came from typedef", .extra = .str, .kind = .note },
590 .{ .msg = "ISO C requires a named parameter before '...'", .kind = .@"error", .suppress_version = .c23 },
591 .{ .msg = "'void' must be the only parameter if specified", .kind = .@"error" },
592 .{ .msg = "'void' parameter cannot be qualified", .kind = .@"error" },
593 .{ .msg = "'void' must be the first parameter if specified", .kind = .@"error" },
594 .{ .msg = "invalid storage class on function parameter", .kind = .@"error" },
595 .{ .msg = "_Thread_local only allowed on variables", .kind = .@"error" },
596 .{ .msg = "'{s}' can only appear on functions", .extra = .str, .kind = .@"error" },
597 .{ .msg = "illegal storage class on function", .kind = .@"error" },
598 .{ .msg = "illegal storage class on global variable", .kind = .@"error" },
599 .{ .msg = "expected statement", .kind = .@"error" },
600 .{ .msg = "function cannot return a function", .kind = .@"error" },
601 .{ .msg = "function cannot return an array", .kind = .@"error" },
602 .{ .msg = "use of undeclared identifier '{s}'", .extra = .str, .kind = .@"error" },
603 .{ .msg = "cannot call non function type '{s}'", .extra = .str, .kind = .@"error" },
604 .{ .msg = "unsupported string literal concatenation", .kind = .@"error" },
605 .{ .msg = "static functions must be global", .kind = .@"error" },
606 .{ .msg = "call to undeclared function '{s}'; ISO C99 and later do not support implicit function declarations", .extra = .str, .opt = W("implicit-function-declaration"), .kind = .@"error", .all = true },
607 .{ .msg = "use of unknown builtin '{s}'", .extra = .str, .opt = W("implicit-function-declaration"), .kind = .@"error", .all = true },
608 .{ .msg = "implicitly declaring library function '{s}'", .extra = .str, .opt = W("implicit-function-declaration"), .kind = .@"error", .all = true },
609 .{ .msg = "include the header <{s}.h> or explicitly provide a declaration for '{s}'", .extra = .builtin_with_header, .opt = W("implicit-function-declaration"), .kind = .note, .all = true },
610 .{ .msg = "expected parameter declaration", .kind = .@"error" },
611 .{ .msg = "identifier parameter lists are only allowed in function definitions", .kind = .@"error" },
612 .{ .msg = "expected function body after function declaration", .kind = .@"error" },
613 .{ .msg = "parameter cannot have void type", .kind = .@"error" },
614 .{ .msg = "expression result unused", .opt = W("unused-value"), .kind = .warning, .all = true },
615 .{ .msg = "'continue' statement not in a loop", .kind = .@"error" },
616 .{ .msg = "'break' statement not in a loop or a switch", .kind = .@"error" },
617 .{ .msg = "unreachable code", .opt = W("unreachable-code"), .kind = .warning, .all = true },
618 .{ .msg = "duplicate label '{s}'", .extra = .str, .kind = .@"error" },
619 .{ .msg = "previous definition of label '{s}' was here", .extra = .str, .kind = .note },
620 .{ .msg = "use of undeclared label '{s}'", .extra = .str, .kind = .@"error" },
621 .{ .msg = "'{s}' statement not in a switch statement", .extra = .str, .kind = .@"error" },
622 .{ .msg = "duplicate case value '{s}'", .extra = .str, .kind = .@"error" },
623 .{ .msg = "multiple default cases in the same switch", .kind = .@"error" },
624 .{ .msg = "previous case defined here", .kind = .note },
625 .{ .msg = expected_arguments, .extra = .arguments, .kind = .@"error" },
626 .{ .msg = "callee declares array parameter as static here", .kind = .note },
627 .{ .msg = "array argument is too small; contains {d} elements, callee requires at least {d}", .extra = .arguments, .kind = .warning, .opt = W("array-bounds") },
628 .{ .msg = "null passed to a callee that requires a non-null argument", .kind = .warning, .opt = W("nonnull") },
629 .{ .msg = expected_arguments, .extra = .arguments, .kind = .warning },
630 .{ .msg = "expected at least {d} argument(s) got {d}", .extra = .arguments, .kind = .warning },
631 .{ .msg = "'static' may not be used with an unspecified variable length array size", .kind = .@"error" },
632 .{ .msg = "'static' used outside of function parameters", .kind = .@"error" },
633 .{ .msg = "type qualifier in non parameter array type", .kind = .@"error" },
634 .{ .msg = "star modifier used outside of function parameters", .kind = .@"error" },
635 .{ .msg = "variable length arrays not allowed at file scope", .kind = .@"error" },
636 .{ .msg = "'static' useless without a constant size", .kind = .warning, .w_extra = true },
637 .{ .msg = "array size must be 0 or greater", .kind = .@"error" },
638 .{ .msg = "array has incomplete element type '{s}'", .extra = .str, .kind = .@"error" },
639 .{ .msg = "arrays cannot have functions as their element type", .kind = .@"error" },
640 .{ .msg = "'static' used in non-outermost array type", .kind = .@"error" },
641 .{ .msg = "type qualifier used in non-outermost array type", .kind = .@"error" },
642 .{ .msg = "unterminated function macro argument list", .kind = .@"error" },
643 .{ .msg = "unknown warning '{s}'", .extra = .str, .opt = W("unknown-warning-option"), .kind = .warning },
644 .{ .msg = "overflow in expression; result is '{s}'", .extra = .str, .opt = W("integer-overflow"), .kind = .warning },
645 .{ .msg = "integer literal is too large to be represented in any integer type", .kind = .@"error" },
646 .{ .msg = "indirection requires pointer operand", .kind = .@"error" },
647 .{ .msg = "cannot take the address of an rvalue", .kind = .@"error" },
648 .{ .msg = "address of bit-field requested", .kind = .@"error" },
649 .{ .msg = "expression is not assignable", .kind = .@"error" },
650 .{ .msg = "expected identifier or '{'", .kind = .@"error" },
651 .{ .msg = "empty enum is invalid", .kind = .@"error" },
652 .{ .msg = "redefinition of '{s}'", .extra = .str, .kind = .@"error" },
653 .{ .msg = "previous definition is here", .kind = .note },
654 .{ .msg = "expected identifier", .kind = .@"error" },
655 .{ .msg = "expected string literal for diagnostic message in static_assert", .kind = .@"error" },
656 .{ .msg = "expected string literal in '{s}'", .extra = .str, .kind = .@"error" },
657 .{ .msg = "parameter named '{s}' is missing", .extra = .str, .kind = .@"error" },
658 .{ .msg = "empty {s} is a GNU extension", .extra = .str, .opt = W("gnu-empty-struct"), .kind = .off, .pedantic = true },
659 .{ .msg = "empty {s} has size 0 in C, size 1 in C++", .extra = .str, .opt = W("c++-compat"), .kind = .off },
660 .{ .msg = "use of '{s}' with tag type that does not match previous definition", .extra = .str, .kind = .@"error" },
661 .{ .msg = "expected parentheses around type name", .kind = .@"error" },
662 .{ .msg = "'_Alignof' applied to an expression is a GNU extension", .opt = W("gnu-alignof-expression"), .kind = .warning, .suppress_gnu = true },
663 .{ .msg = "invalid application of 'alignof' to an incomplete type '{s}'", .extra = .str, .kind = .@"error" },
664 .{ .msg = "invalid application of 'sizeof' to an incomplete type '{s}'", .extra = .str, .kind = .@"error" },
665 .{ .msg = "'{s}' macro redefined", .extra = .str, .opt = W("macro-redefined"), .kind = .warning },
666 .{ .msg = "generic association with qualifiers cannot be matched with", .opt = W("generic-qual-type"), .kind = .warning },
667 .{ .msg = "generic association array type cannot be matched with", .opt = W("generic-qual-type"), .kind = .warning },
668 .{ .msg = "generic association function type cannot be matched with", .opt = W("generic-qual-type"), .kind = .warning },
669 .{ .msg = "type '{s}' in generic association compatible with previously specified type", .extra = .str, .kind = .@"error" },
670 .{ .msg = "compatible type '{s}' specified here", .extra = .str, .kind = .note },
671 .{ .msg = "duplicate default generic association", .kind = .@"error" },
672 .{ .msg = "controlling expression type '{s}' not compatible with any generic association type", .extra = .str, .kind = .@"error" },
673 .{ .msg = "escape sequence out of range", .kind = .@"error" },
674 .{ .msg = "invalid universal character", .kind = .@"error" },
675 .{ .msg = "incomplete universal character name", .kind = .@"error" },
676 .{ .msg = "multi-character character constant", .opt = W("multichar"), .kind = .warning, .all = true },
677 .{ .msg = "{s} character literals may not contain multiple characters", .kind = .@"error", .extra = .str },
678 .{ .msg = "extraneous characters in character constant ignored", .kind = .warning },
679 .{ .msg = "character constant too long for its type", .kind = .warning, .all = true },
680 .{ .msg = "character too large for enclosing character literal type", .kind = .@"error" },
681 .{ .msg = "must use 'struct' tag to refer to type '{s}'", .extra = .str, .kind = .@"error" },
682 .{ .msg = "must use 'union' tag to refer to type '{s}'", .extra = .str, .kind = .@"error" },
683 .{ .msg = "must use 'enum' tag to refer to type '{s}'", .extra = .str, .kind = .@"error" },
684 .{ .msg = "redefinition of '{s}' as different kind of symbol", .extra = .str, .kind = .@"error" },
685 .{ .msg = "redefinition of '{s}' with a different type", .extra = .str, .kind = .@"error" },
686 .{ .msg = "redefinition of parameter '{s}'", .extra = .str, .kind = .@"error" },
687 .{ .msg = "invalid operands to binary expression ({s})", .extra = .str, .kind = .@"error" },
688 .{ .msg = "comparison between pointer and integer ({s})", .extra = .str, .opt = W("pointer-integer-compare"), .kind = .warning },
689 .{ .msg = "comparison of distinct pointer types ({s})", .extra = .str, .opt = W("compare-distinct-pointer-types"), .kind = .warning },
690 .{ .msg = "incompatible pointer types ({s})", .extra = .str, .kind = .@"error" },
691 .{ .msg = "invalid argument type '{s}' to unary expression", .extra = .str, .kind = .@"error" },
692 .{ .msg = "assignment to {s}", .extra = .str, .kind = .@"error" },
693 .{ .msg = "implicit pointer to integer conversion from {s}", .extra = .str, .opt = W("int-conversion"), .kind = .warning },
694 .{ .msg = "pointer cannot be cast to type '{s}'", .extra = .str, .kind = .@"error" },
695 .{ .msg = "operand of type '{s}' cannot be cast to a pointer type", .extra = .str, .kind = .@"error" },
696 .{ .msg = "cannot cast to non arithmetic or pointer type '{s}'", .extra = .str, .kind = .@"error" },
697 .{ .msg = "cast to type '{s}' will not preserve qualifiers", .extra = .str, .opt = W("cast-qualifiers"), .kind = .warning },
698 .{ .msg = "array subscript is not an integer", .kind = .@"error" },
699 .{ .msg = "subscripted value is not an array or pointer", .kind = .@"error" },
700 .{ .msg = "array index {s} is past the end of the array", .extra = .str, .opt = W("array-bounds"), .kind = .warning },
701 .{ .msg = "array index {s} is before the beginning of the array", .extra = .str, .opt = W("array-bounds"), .kind = .warning },
702 .{ .msg = "statement requires expression with integer type ('{s}' invalid)", .extra = .str, .kind = .@"error" },
703 .{ .msg = "statement requires expression with scalar type ('{s}' invalid)", .extra = .str, .kind = .@"error" },
704 .{ .msg = "non-void function '{s}' should return a value", .extra = .str, .opt = W("return-type"), .kind = .@"error", .all = true },
705 .{ .msg = "returning {s}", .extra = .str, .kind = .@"error" },
706 .{ .msg = "returning {s}" ++ pointer_sign_message, .extra = .str, .kind = .warning, .opt = W("pointer-sign") },
707 .{ .msg = "implicit integer to pointer conversion from {s}", .extra = .str, .opt = W("int-conversion"), .kind = .warning },
708 .{ .msg = "non-void function '{s}' does not return a value", .extra = .str, .opt = W("return-type"), .kind = .warning, .all = true },
709 .{ .msg = "void function '{s}' should not return a value", .extra = .str, .opt = W("return-type"), .kind = .@"error", .all = true },
710 .{ .msg = "passing {s}", .extra = .str, .kind = .@"error" },
711 .{ .msg = "passing {s}", .extra = .str, .kind = .warning, .opt = W("incompatible-pointer-types") },
712 .{ .msg = "passing {s}" ++ pointer_sign_message, .extra = .str, .kind = .warning, .opt = W("pointer-sign") },
713 .{ .msg = "passing argument to parameter here", .kind = .note },
714 .{ .msg = "atomic cannot be applied to array type '{s}'", .extra = .str, .kind = .@"error" },
715 .{ .msg = "atomic cannot be applied to function type '{s}'", .extra = .str, .kind = .@"error" },
716 .{ .msg = "atomic cannot be applied to incomplete type '{s}'", .extra = .str, .kind = .@"error" },
717 .{ .msg = "address of register variable requested", .kind = .@"error" },
718 .{ .msg = "variable has incomplete type '{s}'", .extra = .str, .kind = .@"error" },
719 .{ .msg = "parameter has incomplete type '{s}'", .extra = .str, .kind = .@"error" },
720 .{ .msg = "tentative array definition assumed to have one element", .kind = .warning },
721 .{ .msg = "dereferencing pointer to incomplete type '{s}'", .extra = .str, .kind = .@"error" },
722 .{ .msg = "'_Alignas' attribute only applies to variables and fields", .kind = .@"error" },
723 .{ .msg = "'_Alignas' attribute cannot be applied to a function parameter", .kind = .@"error" },
724 .{ .msg = "requested alignment is less than minimum alignment of {d}", .extra = .unsigned, .kind = .@"error" },
725 .{ .msg = "requested alignment of {s} is too large", .extra = .str, .kind = .@"error" },
726 .{ .msg = "requested negative alignment of {s} is invalid", .extra = .str, .kind = .@"error" },
727 .{ .msg = "'_Alignas' attribute is ignored here", .kind = .warning },
728 .{ .msg = "requested alignment of zero is ignored", .kind = .warning },
729 .{ .msg = "requested alignment is not a power of 2", .kind = .@"error" },
730 .{ .msg = "pointer type mismatch ({s})", .extra = .str, .opt = W("pointer-type-mismatch"), .kind = .warning },
731 .{ .msg = "static_assert expression is not an integral constant expression", .kind = .@"error" },
732 .{ .msg = "static_assert with no message is a C23 extension", .opt = W("c23-extensions"), .kind = .warning, .suppress_version = .c23 },
733 .{ .msg = "{s} is incompatible with C standards before C23", .extra = .str, .kind = .off, .suppress_unless_version = .c23, .opt = W("pre-c23-compat") },
734 .{ .msg = "variable length array must be bound in function definition", .kind = .@"error" },
735 .{ .msg = "array is too large", .kind = .@"error" },
736 .{ .msg = "type '{s}' is too large", .kind = .@"error", .extra = .str },
737 .{ .msg = "incompatible pointer types initializing {s}", .extra = .str, .opt = W("incompatible-pointer-types"), .kind = .warning },
738 .{ .msg = "incompatible pointer types initializing {s}" ++ pointer_sign_message, .extra = .str, .opt = W("pointer-sign"), .kind = .warning },
739 .{ .msg = "incompatible pointer types assigning to {s}", .extra = .str, .opt = W("incompatible-pointer-types"), .kind = .warning },
740 .{ .msg = "incompatible pointer types assigning to {s} " ++ pointer_sign_message, .extra = .str, .opt = W("pointer-sign"), .kind = .warning },
741 .{ .msg = "variable-sized object may not be initialized", .kind = .@"error" },
742 .{ .msg = "illegal initializer type", .kind = .@"error" },
743 .{ .msg = "initializing {s}", .extra = .str, .kind = .@"error" },
744 .{ .msg = "scalar initializer cannot be empty", .kind = .@"error" },
745 .{ .msg = "excess elements in scalar initializer", .opt = W("excess-initializers"), .kind = .warning },
746 .{ .msg = "excess elements in string initializer", .opt = W("excess-initializers"), .kind = .warning },
747 .{ .msg = "excess elements in struct initializer", .opt = W("excess-initializers"), .kind = .warning },
748 .{ .msg = "excess elements in array initializer", .opt = W("excess-initializers"), .kind = .warning },
749 .{ .msg = "initializer-string for char array is too long", .opt = W("excess-initializers"), .kind = .warning },
750 .{ .msg = "cannot initialize type ({s})", .extra = .str, .kind = .@"error" },
751 .{ .msg = "'{s} typeof' is invalid", .extra = .str, .kind = .@"error" },
752 .{ .msg = "{s} by zero is undefined", .extra = .str, .opt = W("division-by-zero"), .kind = .warning },
753 .{ .msg = "{s} by zero in preprocessor expression", .extra = .str, .kind = .@"error" },
754 .{ .msg = "'__builtin_choose_expr' requires a constant expression", .kind = .@"error" },
755 .{ .msg = "'_Alignas' attribute requires integer constant expression", .kind = .@"error" },
756 .{ .msg = "case value must be an integer constant expression", .kind = .@"error" },
757 .{ .msg = "enum value must be an integer constant expression", .kind = .@"error" },
758 .{ .msg = "cannot initialize array of type {s}", .extra = .str, .kind = .@"error" },
759 .{ .msg = "array initializer must be an initializer list or wide string literal", .kind = .@"error" },
760 .{ .msg = "initializer overrides previous initialization", .opt = W("initializer-overrides"), .kind = .warning, .w_extra = true },
761 .{ .msg = "previous initialization", .kind = .note },
762 .{ .msg = "array designator used for non-array type '{s}'", .extra = .str, .kind = .@"error" },
763 .{ .msg = "array designator value {s} is negative", .extra = .str, .kind = .@"error" },
764 .{ .msg = "array designator index {s} exceeds array bounds", .extra = .str, .kind = .@"error" },
765 .{ .msg = "field designator used for non-record type '{s}'", .extra = .str, .kind = .@"error" },
766 .{ .msg = "record type has no field named '{s}'", .extra = .str, .kind = .@"error" },
767 .{ .msg = "initializer for aggregate with no elements requires explicit braces", .kind = .@"error" },
768 .{ .msg = "initializing {s} discards qualifiers", .extra = .str, .opt = W("incompatible-pointer-types-discards-qualifiers"), .kind = .warning },
769 .{ .msg = "assigning to {s} discards qualifiers", .extra = .str, .opt = W("incompatible-pointer-types-discards-qualifiers"), .kind = .warning },
770 .{ .msg = "returning {s} discards qualifiers", .extra = .str, .opt = W("incompatible-pointer-types-discards-qualifiers"), .kind = .warning },
771 .{ .msg = "passing {s} discards qualifiers", .extra = .str, .opt = W("incompatible-pointer-types-discards-qualifiers"), .kind = .warning },
772 .{ .msg = "unknown attribute '{s}' ignored", .extra = .str, .opt = W("unknown-attributes"), .kind = .warning },
773 .{ .msg = "{s}", .extra = .str, .opt = W("ignored-attributes"), .kind = .warning },
774 .{ .msg = "fallthrough annotation does not directly precede switch label", .kind = .@"error" },
775 .{ .msg = "'{s}' attribute cannot be applied to a statement", .extra = .str, .kind = .@"error" },
776 .{ .msg = "redefining builtin macro", .opt = W("builtin-macro-redefined"), .kind = .warning },
777 .{ .msg = "builtin feature check macro requires a parenthesized identifier", .kind = .@"error" },
778 .{ .msg = "missing '{s}', after builtin feature-check macro", .extra = .tok_id_expected, .kind = .@"error" },
779 .{ .msg = "use of GNU address-of-label extension", .opt = W("gnu-label-as-value"), .kind = .off, .pedantic = true },
780 .{ .msg = "member reference base type '{s}' is not a structure or union", .extra = .str, .kind = .@"error" },
781 .{ .msg = "member reference type '{s}' is not a pointer; did you mean to use '.'?", .extra = .str, .kind = .@"error" },
782 .{ .msg = "member reference type '{s}' is a pointer; did you mean to use '->'?", .extra = .str, .kind = .@"error" },
783 .{ .msg = "no member named {s}", .extra = .str, .kind = .@"error" },
784 .{ .msg = "{s} expected option name (e.g. \"-Wundef\")", .extra = .str, .opt = W("malformed-warning-check"), .kind = .warning, .all = true },
785 .{ .msg = "computed goto in function with no address-of-label expressions", .kind = .@"error" },
786 .{ .msg = "{s}", .extra = .str, .opt = W("#pragma-messages"), .kind = .warning },
787 .{ .msg = "{s}", .extra = .str, .kind = .@"error" },
788 .{ .msg = "#pragma message: {s}", .extra = .str, .kind = .note },
789 .{ .msg = "pragma {s} requires string literal", .extra = .str, .kind = .@"error" },
790 .{ .msg = "attempt to use a poisoned identifier", .kind = .@"error" },
791 .{ .msg = "can only poison identifier tokens", .kind = .@"error" },
792 .{ .msg = "poisoning existing macro", .kind = .warning },
793 .{ .msg = "no newline at end of file", .opt = W("newline-eof"), .kind = .off, .pedantic = true },
794 .{ .msg = "ISO C requires a translation unit to contain at least one declaration", .opt = W("empty-translation-unit"), .kind = .off, .pedantic = true },
795 .{ .msg = "omitting the parameter name in a function definition is a C23 extension", .opt = W("c23-extensions"), .kind = .warning, .suppress_version = .c23 },
796 .{ .msg = "bit-field has non-integer type '{s}'", .extra = .str, .kind = .@"error" },
797 .{ .msg = "bit-field has negative width ({s})", .extra = .str, .kind = .@"error" },
798 .{ .msg = "named bit-field has zero width", .kind = .@"error" },
799 .{ .msg = "width of bit-field exceeds width of its type", .kind = .@"error" },
800 .{ .msg = "source file is not valid UTF-8", .kind = .@"error" },
801 .{ .msg = "integer literal is too large to be represented in a signed integer type, interpreting as unsigned", .opt = W("implicitly-unsigned-literal"), .kind = .warning },
802 .{ .msg = "token is not a valid binary operator in a preprocessor subexpression", .kind = .@"error" },
803 .{ .msg = "invalid token at start of a preprocessor expression", .kind = .@"error" },
804 .{ .msg = "using this character in an identifier is incompatible with C99", .opt = W("c99-compat"), .kind = .off },
805 .{ .msg = "unexpected character <U+{X:0>4}>", .extra = .actual_codepoint, .kind = .@"error" },
806 .{ .msg = "character <U+{X:0>4}> not allowed at the start of an identifier", .extra = .actual_codepoint, .kind = .@"error" },
807 .{ .msg = "identifier contains Unicode character <U+{X:0>4}> that is invisible in some environments", .opt = W("unicode-homoglyph"), .extra = .actual_codepoint, .kind = .warning },
808 .{ .msg = "treating Unicode character <U+{X:0>4}> as identifier character rather than as '{u}' symbol", .extra = .codepoints, .opt = W("unicode-homoglyph"), .kind = .warning },
809 .{ .msg = "meaningless '{s}' on assembly outside function", .extra = .str, .kind = .@"error" },
810 .{ .msg = "duplicate asm qualifier '{s}'", .extra = .str, .kind = .@"error" },
811 .{ .msg = "cannot use {s} string literal in assembly", .extra = .str, .kind = .@"error" },
812 .{ .msg = "'$' in identifier", .opt = W("dollar-in-identifier-extension"), .kind = .off, .pedantic = true },
813 .{ .msg = "illegal character '$' in identifier", .kind = .@"error" },
814 .{ .msg = "expanded from here", .kind = .note },
815 .{ .msg = "(skipping {d} expansions in backtrace; use -fmacro-backtrace-limit=0 to see all)", .extra = .unsigned, .kind = .note },
816 .{ .msg = "_Pragma requires exactly one string literal token", .kind = .@"error" },
817 .{ .msg = "pragma GCC expected 'error', 'warning', 'diagnostic', 'poison'", .opt = W("unknown-pragmas"), .kind = .off, .all = true },
818 .{ .msg = "pragma GCC diagnostic expected 'error', 'warning', 'ignored', 'fatal', 'push', or 'pop'", .opt = W("unknown-pragmas"), .kind = .warning, .all = true },
819 .{ .msg = "predefined identifier is only valid inside function", .opt = W("predefined-identifier-outside-function"), .kind = .warning },
820 .{ .msg = "first argument to va_arg, is of type '{s}' and not 'va_list'", .extra = .str, .kind = .@"error" },
821 .{ .msg = "too many braces around scalar initializer", .opt = W("many-braces-around-scalar-init"), .kind = .warning },
822 .{ .msg = "variable '{s}' is uninitialized when used within its own initialization", .extra = .str, .opt = W("uninitialized"), .kind = .off, .all = true },
823 .{ .msg = "use of GNU statement expression extension", .opt = W("gnu-statement-expression"), .kind = .off, .suppress_gnu = true, .pedantic = true },
824 .{ .msg = "statement expression not allowed at file scope", .kind = .@"error" },
825 .{ .msg = "imaginary constants are a GNU extension", .opt = W("gnu-imaginary-constant"), .kind = .off, .suppress_gnu = true, .pedantic = true },
826 .{ .msg = "plain '_Complex' requires a type specifier; assuming '_Complex double'", .kind = .warning },
827 .{ .msg = "complex integer types are a GNU extension", .opt = W("gnu-complex-integer"), .suppress_gnu = true, .kind = .off },
828 .{ .msg = "'{s}' type qualifier on return type has no effect", .opt = W("ignored-qualifiers"), .extra = .str, .kind = .off, .all = true },
829 .{ .msg = "invalid standard '{s}'", .extra = .str, .kind = .@"error" },
830 .{ .msg = "invalid target '{s}'", .extra = .str, .kind = .@"error" },
831 .{ .msg = "invalid compiler '{s}'", .extra = .str, .kind = .@"error" },
832 .{ .msg = "unknown argument '{s}'", .extra = .str, .kind = .@"error" },
833 .{ .msg = "{s}", .extra = .str, .kind = .@"error" },
834 .{ .msg = "{s}: linker input file unused because linking not done", .extra = .str, .kind = .warning },
835 .{ .msg = "unrecognized linker '{s}'", .extra = .str, .kind = .@"error" },
836 .{ .msg = "extra ';' outside of a function", .opt = W("extra-semi"), .kind = .off, .pedantic = true },
837 .{ .msg = "field declared as a function", .kind = .@"error" },
838 .{ .msg = "variable length array fields extension is not supported", .kind = .@"error" },
839 .{ .msg = "field has incomplete type '{s}'", .extra = .str, .kind = .@"error" },
840 .{ .msg = "flexible array member in union is not allowed", .kind = .@"error", .suppress_msvc = true },
841 .{ .msg = "flexible array member is not at the end of struct", .kind = .@"error" },
842 .{ .msg = "flexible array member in otherwise empty struct", .kind = .@"error", .suppress_msvc = true },
843 .{ .msg = "duplicate member '{s}'", .extra = .str, .kind = .@"error" },
844 .{ .msg = "binary integer literals are a GNU extension", .kind = .off, .opt = W("gnu-binary-literal"), .pedantic = true },
845 .{ .msg = "named variadic macros are a GNU extension", .opt = W("variadic-macros"), .kind = .off, .pedantic = true },
846 .{ .msg = "builtin function must be directly called", .kind = .@"error" },
847 .{ .msg = "'va_start' cannot be used outside a function", .kind = .@"error" },
848 .{ .msg = "'va_start' used in a function with fixed args", .kind = .@"error" },
849 .{ .msg = "second argument to 'va_start' is not the last named parameter", .opt = W("varargs"), .kind = .warning },
850 .{ .msg = "'{s}' attribute takes at least {d} argument(s)", .kind = .@"error", .extra = .attr_arg_count },
851 .{ .msg = "'{s}' attribute takes at most {d} argument(s)", .kind = .@"error", .extra = .attr_arg_count },
852 .{ .msg = "Attribute argument is invalid, expected {s} but got {s}", .kind = .@"error", .extra = .attr_arg_type },
853 .{ .msg = "Unknown `{s}` argument. Possible values are: {s}", .kind = .@"error", .extra = .attr_enum },
854 .{ .msg = "'{s}' attribute requires an identifier", .kind = .@"error", .extra = .str },
855 .{ .msg = "'__declspec' attributes are not enabled; use '-fdeclspec' or '-fms-extensions' to enable support for __declspec attributes", .kind = .@"error" },
856 .{ .msg = "__declspec attribute '{s}' is not supported", .extra = .str, .opt = W("ignored-attributes"), .kind = .warning },
857 .{ .msg = "{s}", .extra = .str, .opt = W("deprecated-declarations"), .kind = .warning },
858 .{ .msg = "'{s}' has been explicitly marked deprecated here", .extra = .str, .opt = W("deprecated-declarations"), .kind = .note },
859 .{ .msg = "{s}", .extra = .str, .kind = .@"error" },
860 .{ .msg = "'{s}' has been explicitly marked unavailable here", .extra = .str, .kind = .note },
861 .{ .msg = "{s}", .extra = .str, .kind = .warning, .opt = W("attribute-warning") },
862 .{ .msg = "{s}", .extra = .str, .kind = .@"error" },
863 .{ .msg = "attribute '{s}' is ignored, place it after \"{s}\" to apply attribute to type declaration", .extra = .ignored_record_attr, .kind = .warning, .opt = W("ignored-attributes") },
864 .{ .msg = "backslash and newline separated by space", .kind = .warning, .opt = W("backslash-newline-escape") },
865 .{ .msg = "size of array has non-integer type '{s}'", .extra = .str, .kind = .@"error" },
866 .{ .msg = "cast to smaller integer type {s}", .extra = .str, .kind = .warning, .opt = W("pointer-to-int-cast") },
867 .{ .msg = "use of GNU case range extension", .opt = W("gnu-case-range"), .kind = .off, .pedantic = true },
868 .{ .msg = "empty case range specified", .kind = .warning },
869 .{ .msg = "use of non-standard escape character '\\{s}'", .kind = .off, .opt = W("pedantic"), .extra = .invalid_escape },
870 .{ .msg = "invalid string literal, ignoring final '\\'", .kind = .warning },
871 .{ .msg = "variable length array used", .kind = .off, .opt = W("vla") },
872 .{ .msg = "implicit conversion from {s}", .extra = .str, .kind = .warning, .opt = W("constant-conversion") },
873 .{ .msg = "implicit conversion changes signedness: {s}", .extra = .str, .kind = .off, .opt = W("sign-conversion") },
874 .{ .msg = "implicit conversion of non-finite value from {s} is undefined", .extra = .str, .kind = .off, .opt = W("float-overflow-conversion") },
875 .{ .msg = "implicit conversion of out of range value from {s} is undefined", .extra = .str, .kind = .warning, .opt = W("literal-conversion") },
876 .{ .msg = "implicit conversion from {s}", .extra = .str, .kind = .off, .opt = W("float-zero-conversion") },
877 .{ .msg = "implicit conversion from {s}", .extra = .str, .kind = .warning, .opt = W("float-conversion") },
878 .{ .msg = "implicit conversion turns floating-point number into integer: {s}", .extra = .str, .kind = .off, .opt = W("literal-conversion") },
879 .{ .msg = "expression is not an integer constant expression; folding it to a constant is a GNU extension", .kind = .off, .opt = W("gnu-folding-constant"), .pedantic = true },
880 .{ .msg = "variable length array folded to constant array as an extension", .kind = .off, .opt = W("gnu-folding-constant"), .pedantic = true },
881 .{ .msg = "typedef redefinition with different types ({s})", .extra = .str, .kind = .@"error" },
882 .{ .msg = "'{s}' is not defined, evaluates to 0", .extra = .str, .kind = .off, .opt = W("undef") },
883 .{ .msg = "function-like macro '{s}' is not defined", .extra = .str, .kind = .@"error" },
884 .{ .msg = "'{s}' must be used within a preprocessing directive", .extra = .tok_id_expected, .kind = .@"error" },
885 .{ .msg = "Missing '(' after built-in macro '{s}'", .extra = .str, .kind = .@"error" },
886 .{ .msg = "offsetof requires struct or union type, '{s}' invalid", .extra = .str, .kind = .@"error" },
887 .{ .msg = "offsetof of incomplete type '{s}'", .extra = .str, .kind = .@"error" },
888 .{ .msg = "offsetof requires array type, '{s}' invalid", .extra = .str, .kind = .@"error" },
889 .{ .msg = "missing '(' after '#pragma pack' - ignoring", .kind = .warning, .opt = W("ignored-pragmas") },
890 .{ .msg = "missing ')' after '#pragma pack' - ignoring", .kind = .warning, .opt = W("ignored-pragmas") },
891 .{ .msg = "unknown action for '#pragma pack' - ignoring", .opt = W("ignored-pragmas"), .kind = .warning },
892 .{ .msg = "value of #pragma pack(show) == {d}", .extra = .unsigned, .kind = .warning },
893 .{ .msg = "expected #pragma pack parameter to be '1', '2', '4', '8', or '16'", .opt = W("ignored-pragmas"), .kind = .warning },
894 .{ .msg = "expected integer or identifier in '#pragma pack' - ignored", .opt = W("ignored-pragmas"), .kind = .warning },
895 .{ .msg = "specifying both a name and alignment to 'pop' is undefined", .kind = .warning },
896 .{ .msg = "#pragma pack(pop, ...) failed: stack empty", .opt = W("ignored-pragmas"), .kind = .warning },
897 .{ .msg = "used type '{s}' where arithmetic or pointer type is required", .extra = .str, .kind = .@"error" },
898 .{ .msg = "#include nested too deeply", .kind = .@"error" },
899 .{ .msg = "ISO C restricts enumerator values to range of 'int' ({s} is too small)", .extra = .str, .kind = .off, .opt = W("pedantic") },
900 .{ .msg = "ISO C restricts enumerator values to range of 'int' ({s} is too large)", .extra = .str, .kind = .off, .opt = W("pedantic") },
901 .{ .msg = "#include_next is a language extension", .kind = .off, .pedantic = true, .opt = W("gnu-include-next") },
902 .{ .msg = "#include_next in primary source file; will search from start of include path", .kind = .warning, .opt = W("include-next-outside-header") },
903 .{ .msg = "overflow in enumeration value", .kind = .warning },
904 .{ .msg = "incremented enumerator value {s} is not representable in the largest integer type", .kind = .warning, .opt = W("enum-too-large"), .extra = .pow_2_as_string },
905 .{ .msg = "enumeration values exceed range of largest integer", .kind = .warning, .opt = W("enum-too-large") },
906 .{ .msg = "enumeration types with a fixed underlying type are a Clang extension", .kind = .off, .pedantic = true, .opt = W("fixed-enum-extension") },
907 .{ .msg = "enumeration previously declared with nonfixed underlying type", .kind = .@"error" },
908 .{ .msg = "enumeration previously declared with fixed underlying type", .kind = .@"error" },
909 .{ .msg = "enumeration redeclared with different underlying type {s})", .extra = .str, .kind = .@"error" },
910 .{ .msg = "enumerator value is not representable in the underlying type '{s}'", .extra = .str, .kind = .@"error" },
911 .{ .msg = "'transparent_union' attribute only applies to unions", .opt = W("ignored-attributes"), .kind = .warning },
912 .{ .msg = "transparent union definition must contain at least one field; transparent_union attribute ignored", .opt = W("ignored-attributes"), .kind = .warning },
913 .{ .msg = "size of field {s} bits) does not match the size of the first field in transparent union; transparent_union attribute ignored", .extra = .str, .opt = W("ignored-attributes"), .kind = .warning },
914 .{ .msg = "size of first field is {d}", .extra = .unsigned, .kind = .note },
915 .{ .msg = "'designated_init' attribute is only valid on 'struct' type'", .kind = .@"error" },
916 .{ .msg = "positional initialization of field in 'struct' declared with 'designated_init' attribute", .opt = W("designated-init"), .kind = .warning },
917 .{ .msg = "ignoring attribute 'common' because it conflicts with attribute 'nocommon'", .opt = W("ignored-attributes"), .kind = .warning },
918 .{ .msg = "ignoring attribute 'nocommon' because it conflicts with attribute 'common'", .opt = W("ignored-attributes"), .kind = .warning },
919 .{ .msg = "'nonstring' attribute ignored on objects of type '{s}'", .opt = W("ignored-attributes"), .kind = .warning },
920 .{ .msg = "'{s}' attribute only applies to local variables", .extra = .str, .opt = W("ignored-attributes"), .kind = .warning },
921 .{ .msg = "ignoring attribute 'cold' because it conflicts with attribute 'hot'", .opt = W("ignored-attributes"), .kind = .warning },
922 .{ .msg = "ignoring attribute 'hot' because it conflicts with attribute 'cold'", .opt = W("ignored-attributes"), .kind = .warning },
923 .{ .msg = "ignoring attribute 'noinline' because it conflicts with attribute 'always_inline'", .opt = W("ignored-attributes"), .kind = .warning },
924 .{ .msg = "ignoring attribute 'always_inline' because it conflicts with attribute 'noinline'", .opt = W("ignored-attributes"), .kind = .warning },
925 .{ .msg = "function '{s}' declared 'noreturn' should not return", .extra = .str, .kind = .warning, .opt = W("invalid-noreturn") },
926 .{ .msg = "ignoring return value of '{s}', declared with 'nodiscard' attribute", .extra = .str, .kind = .warning, .opt = W("unused-result") },
927 .{ .msg = "ignoring return value of '{s}', declared with 'warn_unused_result' attribute", .extra = .str, .kind = .warning, .opt = W("unused-result") },
928 .{ .msg = "invalid vector element type '{s}'", .extra = .str, .kind = .@"error" },
929 .{ .msg = "vector size not an integral multiple of component size", .kind = .@"error" },
930 .{ .msg = "invalid type '{s}' to __imag operator", .extra = .str, .kind = .@"error" },
931 .{ .msg = "invalid type '{s}' to __real operator", .extra = .str, .kind = .@"error" },
932 .{ .msg = "zero size arrays are an extension", .kind = .off, .pedantic = true, .opt = W("zero-length-array") },
933 .{ .msg = "array index {s} is past the end of the array", .extra = .str, .kind = .off, .pedantic = true, .opt = W("old-style-flexible-struct") },
934 .{ .msg = "token pasting of ',' and __VA_ARGS__ is a GNU extension", .kind = .off, .pedantic = true, .opt = W("gnu-zero-variadic-macro-arguments"), .suppress_gcc = true },
935 .{ .msg = "return type of 'main' is not 'int'", .kind = .warning, .opt = W("main-return-type") },
936 .{ .msg = "macro expansion producing 'defined' has undefined behavior", .kind = .off, .pedantic = true, .opt = W("expansion-to-defined") },
937 .{ .msg = "invalid suffix '{s}' on integer constant", .extra = .str, .kind = .@"error" },
938 .{ .msg = "invalid suffix '{s}' on floating constant", .extra = .str, .kind = .@"error" },
939 .{ .msg = "invalid digit '{c}' in octal constant", .extra = .ascii, .kind = .@"error" },
940 .{ .msg = "invalid digit '{c}' in binary constant", .extra = .ascii, .kind = .@"error" },
941 .{ .msg = "exponent has no digits", .kind = .@"error" },
942 .{ .msg = "hexadecimal floating constant requires an exponent", .kind = .@"error" },
943 .{ .msg = "sizeof returns 0", .kind = .warning, .suppress_gcc = true, .suppress_clang = true },
944 .{ .msg = "'declspec' attribute not allowed after declarator", .kind = .@"error" },
945 .{ .msg = "this declarator", .kind = .note },
946 .{ .msg = "{s} is not supported on this target", .extra = .str, .kind = .@"error" },
947 .{ .msg = "'_BitInt' in C17 and earlier is a Clang extension'", .kind = .off, .pedantic = true, .opt = W("bit-int-extension"), .suppress_version = .c23 },
948 .{ .msg = "{s}unsigned _BitInt must have a bit size of at least 1", .extra = .str, .kind = .@"error" },
949 .{ .msg = "{s}signed _BitInt must have a bit size of at least 2", .extra = .str, .kind = .@"error" },
950 .{ .msg = "{s}unsigned _BitInt of bit sizes greater than " ++ std.fmt.comptimePrint("{d}", .{Properties.max_bits}) ++ " not supported", .extra = .str, .kind = .@"error" },
951 .{ .msg = "{s}signed _BitInt of bit sizes greater than " ++ std.fmt.comptimePrint("{d}", .{Properties.max_bits}) ++ " not supported", .extra = .str, .kind = .@"error" },
952 .{ .msg = "keyword is hidden by macro definition", .kind = .off, .pedantic = true, .opt = W("keyword-macro") },
953 .{ .msg = "arithmetic on a pointer to an incomplete type '{s}'", .extra = .str, .kind = .@"error" },
954 .{ .msg = "'{s}' calling convention is not supported for this target", .extra = .str, .opt = W("ignored-attributes"), .kind = .warning },
955 .{ .msg = "invalid application of '{s}' to a void type", .extra = .str, .kind = .off, .pedantic = true, .opt = W("pointer-arith") },
956 .{ .msg = "sizeof on array function parameter will return size of {s}", .extra = .str, .kind = .warning, .opt = W("sizeof-array-argument") },
957 .{ .msg = "address of array '{s}' will always evaluate to 'true'", .extra = .str, .kind = .warning, .opt = W("pointer-bool-conversion") },
958 .{ .msg = "implicit conversion turns string literal into bool: {s}", .extra = .str, .kind = .off, .opt = W("string-conversion") },
959 .{ .msg = "this conversion is not allowed in a constant expression", .kind = .note },
960 .{ .msg = "cannot cast an object of type {s}", .extra = .str, .kind = .@"error" },
961 .{ .msg = "unsupported argument '{s}' to option '-ffp-eval-method='; expected 'source', 'double', or 'extended'", .extra = .str, .kind = .@"error" },
962 .{ .msg = "{s} cannot have __fp16 type; did you forget * ?", .extra = .str, .kind = .@"error" },
963 .{ .msg = "'_BitInt' suffix for literals is a C23 extension", .opt = W("c23-extensions"), .kind = .warning, .suppress_version = .c23 },
964 .{ .msg = "'__auto_type' is a GNU extension", .opt = W("gnu-auto-type"), .kind = .off, .pedantic = true },
965 .{ .msg = "'__auto_type' not allowed in {s}", .kind = .@"error", .extra = .str },
966 .{ .msg = "declaration of variable '{s}' with deduced type requires an initializer", .kind = .@"error", .extra = .str },
967 .{ .msg = "'__auto_type' may only be used with a single declarator", .kind = .@"error" },
968 .{ .msg = "'__auto_type' requires a plain identifier as declarator", .kind = .@"error" },
969 .{ .msg = "invalid cast to '__auto_type'", .kind = .@"error" },
970 .{ .msg = "cannot use bit-field as '__auto_type' initializer", .kind = .@"error" },
971 .{ .msg = "'{s}' declared as array of '__auto_type'", .kind = .@"error", .extra = .str },
972 .{ .msg = "cannot use '__auto_type' with initializer list", .kind = .@"error" },
973 .{ .msg = "expected ';' at end of declaration list", .kind = .warning },
974 .{ .msg = "tentative definition has type '{s}' that is never completed", .kind = .@"error", .extra = .str },
975 .{ .msg = "forward declaration of '{s}'", .kind = .note, .extra = .str },
976 .{ .msg = "cast to union type is a GNU extension", .opt = W("gnu-union-cast"), .kind = .off, .pedantic = true },
977 .{ .msg = "cast to union type from type '{s}' not present in union", .kind = .@"error", .extra = .str },
978 .{ .msg = "cast to incomplete type '{s}'", .kind = .@"error", .extra = .str },
979 .{ .msg = "environment variable SOURCE_DATE_EPOCH must expand to a non-negative integer less than or equal to 253402300799", .kind = .@"error" },
980 .{ .msg = "'-fuse-ld=' taking a path is deprecated; use '--ld-path=' instead", .kind = .off, .opt = W("fuse-ld-path") },
981 .{ .msg = "invalid runtime library name '{s}'", .kind = .@"error", .extra = .str },
982 .{ .msg = "unsupported runtime library 'libgcc' for platform '{s}'", .kind = .@"error", .extra = .str },
983 .{ .msg = "invalid unwind library name '{s}'", .kind = .@"error", .extra = .str },
984 .{ .msg = "--rtlib=libgcc requires --unwindlib=libgcc", .kind = .@"error" },
985 .{ .msg = "GNU-style inline assembly is disabled", .kind = .@"error" },
986 .{ .msg = "extension used", .kind = .off, .pedantic = true, .opt = W("language-extension-token") },
987 .{ .msg = "complex initialization specifying real and imaginary components is an extension", .opt = W("complex-component-init"), .kind = .off, .pedantic = true },
988 .{ .msg = "ISO C does not support '++'/'--' on complex type '{s}'", .opt = W("pedantic"), .extra = .str, .kind = .off },
989 .{ .msg = "argument type '{s}' is not a real floating point type", .extra = .str, .kind = .@"error" },
990 .{ .msg = "arguments are of different types ({s})", .extra = .str, .kind = .@"error" },
991 .{ .msg = "#include resolved using non-portable Microsoft search rules as: {s}", .extra = .str, .opt = W("microsoft-include"), .kind = .warning },
992 .{ .msg = "treating Ctrl-Z as end-of-file is a Microsoft extension", .opt = W("microsoft-end-of-file"), .kind = .off, .pedantic = true },
993 .{ .msg = "illegal character encoding in character literal", .opt = W("invalid-source-encoding"), .kind = .warning },
994 .{ .msg = "illegal character encoding in character literal", .kind = .@"error" },
995 .{ .msg = "character '{c}' cannot be specified by a universal character name", .kind = .@"error", .extra = .ascii },
996 .{ .msg = "specifying character '{c}' with a universal character name is incompatible with C standards before C23", .kind = .off, .extra = .ascii, .suppress_unless_version = .c23, .opt = W("pre-c23-compat") },
997 .{ .msg = "universal character name refers to a control character", .kind = .@"error" },
998 .{ .msg = "universal character name referring to a control character is incompatible with C standards before C23", .kind = .off, .suppress_unless_version = .c23, .opt = W("pre-c23-compat") },
999 .{ .msg = "universal character names are only valid in C99 or later", .suppress_version = .c99, .kind = .warning, .opt = W("unicode") },
1000 .{ .msg = "multi-character character constant", .opt = W("four-char-constants"), .kind = .off },
1001 .{ .msg = "multi-character character constant", .kind = .off },
1002 .{ .msg = "\\{c} used with no following hex digits", .kind = .@"error", .extra = .ascii },
1003 .{ .msg = "unknown escape sequence '\\{s}'", .kind = .warning, .opt = W("unknown-escape-sequence"), .extra = .invalid_escape },
1004 .{ .msg = "attribute '{s}' requires an ordinary string", .kind = .@"error", .extra = .str },
1005 .{ .msg = "missing terminating '\"' character", .kind = .warning, .opt = W("invalid-pp-token") },
1006 .{ .msg = "missing terminating '\"' character", .kind = .@"error" },
1007 .{ .msg = "empty character constant", .kind = .warning, .opt = W("invalid-pp-token") },
1008 .{ .msg = "empty character constant", .kind = .@"error" },
1009 .{ .msg = "missing terminating ' character", .kind = .warning, .opt = W("invalid-pp-token") },
1010 .{ .msg = "missing terminating ' character", .kind = .@"error" },
1011 .{ .msg = "unterminated comment", .kind = .@"error" },
1012 .{ .msg = "a function definition without a prototype is deprecated in all versions of C and is not supported in C23", .kind = .warning, .opt = W("deprecated-non-prototype") },
1013 .{ .msg = "passing arguments to a function without a prototype is deprecated in all versions of C and is not supported in C23", .kind = .warning, .opt = W("deprecated-non-prototype") },
1014 .{ .msg = "unknown type name '{s}'", .kind = .@"error", .extra = .str },
1015 .{ .msg = "label at end of compound statement is a C23 extension", .opt = W("c23-extensions"), .kind = .warning, .suppress_version = .c23 },
1016 .{ .msg = "UTF-8 character literal is a C23 extension", .opt = W("c23-extensions"), .kind = .warning, .suppress_version = .c23 },
1017 .{ .msg = "unexpected token in embed parameter", .kind = .@"error" },
1018 .{ .msg = "the limit parameter expects one non-negative integer as a parameter", .kind = .@"error" },
1019 .{ .msg = "duplicate embed parameter '{s}'", .kind = .warning, .extra = .str, .opt = W("duplicate-embed-param") },
1020 .{ .msg = "unsupported embed parameter '{s}' embed parameter", .kind = .warning, .extra = .str, .opt = W("unsupported-embed-param") },
1021 .{ .msg = "compound literal cannot have {s} storage class", .kind = .@"error", .extra = .str },
1022 .{ .msg = "missing '(' following __VA_OPT__", .kind = .@"error" },
1023 .{ .msg = "unterminated __VA_OPT__ argument list", .kind = .@"error" },
1024 .{ .msg = "attribute value '{s}' out of range", .kind = .@"error", .extra = .str },
1025 .{ .msg = "'{s}' is not in NFC", .kind = .warning, .extra = .normalized, .opt = W("normalized") },
1026 .{ .msg = "'auto' requires a plain identifier declarator", .kind = .@"error" },
1027 .{ .msg = "'auto' can only be used with a single declarator", .kind = .@"error" },
1028 .{ .msg = "'auto' requires an initializer", .kind = .@"error" },
1029 .{ .msg = "'auto' requires a scalar initializer", .kind = .@"error" },
1030 .{ .msg = "shift count is negative", .opt = W("shift-count-negative"), .kind = .warning, .all = true },
1031 .{ .msg = "shift count >= width of type", .opt = W("shift-count-overflow"), .kind = .warning, .all = true },
1032 .{ .msg = "ISO C does not support '~' for complex conjugation of '{s}'", .opt = W("pedantic"), .extra = .str, .kind = .off },
1033 .{ .msg = "operand argument to overflow builtin must be an integer ('{s}' invalid)", .extra = .str, .kind = .@"error" },
1034 .{ .msg = "result argument to overflow builtin must be a pointer to a non-const integer ('{s}' invalid)", .extra = .str, .kind = .@"error" },
1035 .{ .msg = "TODO: implement '{s}' attribute for {s}", .extra = .attribute_todo, .kind = .@"error" },
1036 .{ .msg = "non-integral type '{s}' is an invalid underlying type", .extra = .str, .kind = .@"error" },
1037 .{ .msg = "variable '{s}' declared with deduced type '__auto_type' cannot appear in its own initializer", .extra = .str, .kind = .@"error" },
1038 };
1039};
1040};
1041}
lib/compiler/aro/aro/Driver.zig deleted-863
...@@ -1,863 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const Allocator = mem.Allocator;
4const process = std.process;
5const backend = @import("../backend.zig");
6const Ir = backend.Ir;
7const Object = backend.Object;
8const Compilation = @import("Compilation.zig");
9const Diagnostics = @import("Diagnostics.zig");
10const LangOpts = @import("LangOpts.zig");
11const Preprocessor = @import("Preprocessor.zig");
12const Source = @import("Source.zig");
13const Toolchain = @import("Toolchain.zig");
14const target_util = @import("target.zig");
15const GCCVersion = @import("Driver/GCCVersion.zig");
16
17pub const Linker = enum {
18 ld,
19 bfd,
20 gold,
21 lld,
22 mold,
23};
24
25const Driver = @This();
26
27comp: *Compilation,
28inputs: std.ArrayListUnmanaged(Source) = .empty,
29link_objects: std.ArrayListUnmanaged([]const u8) = .empty,
30output_name: ?[]const u8 = null,
31sysroot: ?[]const u8 = null,
32system_defines: Compilation.SystemDefinesMode = .include_system_defines,
33temp_file_count: u32 = 0,
34/// If false, do not emit line directives in -E mode
35line_commands: bool = true,
36/// If true, use `#line <num>` instead of `# <num>` for line directives
37use_line_directives: bool = false,
38only_preprocess: bool = false,
39only_syntax: bool = false,
40only_compile: bool = false,
41only_preprocess_and_compile: bool = false,
42verbose_ast: bool = false,
43verbose_pp: bool = false,
44verbose_ir: bool = false,
45verbose_linker_args: bool = false,
46color: ?bool = null,
47nobuiltininc: bool = false,
48nostdinc: bool = false,
49nostdlibinc: bool = false,
50debug_dump_letters: packed struct(u3) {
51 d: bool = false,
52 m: bool = false,
53 n: bool = false,
54
55 /// According to GCC, specifying letters whose behavior conflicts is undefined.
56 /// We follow clang in that `-dM` always takes precedence over `-dD`
57 pub fn getPreprocessorDumpMode(self: @This()) Preprocessor.DumpMode {
58 if (self.m) return .macros_only;
59 if (self.d) return .macros_and_result;
60 if (self.n) return .macro_names_and_result;
61 return .result_only;
62 }
63} = .{},
64
65/// Full path to the aro executable
66aro_name: []const u8 = "",
67
68/// Value of --triple= passed via CLI
69raw_target_triple: ?[]const u8 = null,
70
71// linker options
72use_linker: ?[]const u8 = null,
73linker_path: ?[]const u8 = null,
74nodefaultlibs: bool = false,
75nolibc: bool = false,
76nostartfiles: bool = false,
77nostdlib: bool = false,
78pie: ?bool = null,
79rdynamic: bool = false,
80relocatable: bool = false,
81rtlib: ?[]const u8 = null,
82shared: bool = false,
83shared_libgcc: bool = false,
84static: bool = false,
85static_libgcc: bool = false,
86static_pie: bool = false,
87strip: bool = false,
88unwindlib: ?[]const u8 = null,
89
90pub fn deinit(d: *Driver) void {
91 for (d.link_objects.items[d.link_objects.items.len - d.temp_file_count ..]) |obj| {
92 std.fs.deleteFileAbsolute(obj) catch {};
93 d.comp.gpa.free(obj);
94 }
95 d.inputs.deinit(d.comp.gpa);
96 d.link_objects.deinit(d.comp.gpa);
97 d.* = undefined;
98}
99
100pub const usage =
101 \\Usage {s}: [options] file..
102 \\
103 \\General options:
104 \\ -h, --help Print this message.
105 \\ -v, --version Print aro version.
106 \\
107 \\Compile options:
108 \\ -c, --compile Only run preprocess, compile, and assemble steps
109 \\ -dM Output #define directives for all the macros defined during the execution of the preprocessor
110 \\ -dD Like -dM except that it outputs both the #define directives and the result of preprocessing
111 \\ -dN Like -dD, but emit only the macro names, not their expansions.
112 \\ -D <macro>=<value> Define <macro> to <value> (defaults to 1)
113 \\ -E Only run the preprocessor
114 \\ -fchar8_t Enable char8_t (enabled by default in C23 and later)
115 \\ -fno-char8_t Disable char8_t (disabled by default for pre-C23)
116 \\ -fcolor-diagnostics Enable colors in diagnostics
117 \\ -fno-color-diagnostics Disable colors in diagnostics
118 \\ -fdeclspec Enable support for __declspec attributes
119 \\ -fgnuc-version=<value> Controls value of __GNUC__ and related macros. Set to 0 or empty to disable them.
120 \\ -fno-declspec Disable support for __declspec attributes
121 \\ -ffp-eval-method=[source|double|extended]
122 \\ Evaluation method to use for floating-point arithmetic
123 \\ -ffreestanding Compilation in a freestanding environment
124 \\ -fgnu-inline-asm Enable GNU style inline asm (default: enabled)
125 \\ -fno-gnu-inline-asm Disable GNU style inline asm
126 \\ -fhosted Compilation in a hosted environment
127 \\ -fms-extensions Enable support for Microsoft extensions
128 \\ -fno-ms-extensions Disable support for Microsoft extensions
129 \\ -fdollars-in-identifiers
130 \\ Allow '$' in identifiers
131 \\ -fno-dollars-in-identifiers
132 \\ Disallow '$' in identifiers
133 \\ -fmacro-backtrace-limit=<limit>
134 \\ Set limit on how many macro expansion traces are shown in errors (default 6)
135 \\ -fnative-half-type Use the native half type for __fp16 instead of promoting to float
136 \\ -fnative-half-arguments-and-returns
137 \\ Allow half-precision function arguments and return values
138 \\ -fshort-enums Use the narrowest possible integer type for enums
139 \\ -fno-short-enums Use "int" as the tag type for enums
140 \\ -fsigned-char "char" is signed
141 \\ -fno-signed-char "char" is unsigned
142 \\ -fsyntax-only Only run the preprocessor, parser, and semantic analysis stages
143 \\ -funsigned-char "char" is unsigned
144 \\ -fno-unsigned-char "char" is signed
145 \\ -fuse-line-directives Use `#line <num>` linemarkers in preprocessed output
146 \\ -fno-use-line-directives
147 \\ Use `# <num>` linemarkers in preprocessed output
148 \\ -I <dir> Add directory to include search path
149 \\ -isystem Add directory to SYSTEM include search path
150 \\ --emulate=[clang|gcc|msvc]
151 \\ Select which C compiler to emulate (default clang)
152 \\ -nobuiltininc Do not search the compiler's builtin directory for include files
153 \\ -nostdinc, --no-standard-includes
154 \\ Do not search the standard system directories or compiler builtin directories for include files.
155 \\ -nostdlibinc Do not search the standard system directories for include files, but do search compiler builtin include directories
156 \\ -o <file> Write output to <file>
157 \\ -P, --no-line-commands Disable linemarker output in -E mode
158 \\ -pedantic Warn on language extensions
159 \\ --rtlib=<arg> Compiler runtime library to use (libgcc or compiler-rt)
160 \\ -std=<standard> Specify language standard
161 \\ -S, --assemble Only run preprocess and compilation steps
162 \\ --sysroot=<dir> Use dir as the logical root directory for headers and libraries (not fully implemented)
163 \\ --target=<value> Generate code for the given target
164 \\ -U <macro> Undefine <macro>
165 \\ -undef Do not predefine any system-specific macros. Standard predefined macros remain defined.
166 \\ -Werror Treat all warnings as errors
167 \\ -Werror=<warning> Treat warning as error
168 \\ -W<warning> Enable the specified warning
169 \\ -Wno-<warning> Disable the specified warning
170 \\
171 \\Link options:
172 \\ -fuse-ld=[bfd|gold|lld|mold]
173 \\ Use specific linker
174 \\ -nodefaultlibs Do not use the standard system libraries when linking.
175 \\ -nolibc Do not use the C library or system libraries tightly coupled with it when linking.
176 \\ -nostdlib Do not use the standard system startup files or libraries when linking
177 \\ -nostartfiles Do not use the standard system startup files when linking.
178 \\ -pie Produce a dynamically linked position independent executable on targets that support it.
179 \\ --ld-path=<path> Use linker specified by <path>
180 \\ -r Produce a relocatable object as output.
181 \\ -rdynamic Pass the flag -export-dynamic to the ELF linker, on targets that support it.
182 \\ -s Remove all symbol table and relocation information from the executable.
183 \\ -shared Produce a shared object which can then be linked with other objects to form an executable.
184 \\ -shared-libgcc On systems that provide libgcc as a shared library, force the use of the shared version
185 \\ -static On systems that support dynamic linking, this overrides -pie and prevents linking with the shared libraries.
186 \\ -static-libgcc On systems that provide libgcc as a shared library, force the use of the static version
187 \\ -static-pie Produce a static position independent executable on targets that support it.
188 \\ --unwindlib=<arg> Unwind library to use ("none", "libgcc", or "libunwind") If not specified, will match runtime library
189 \\
190 \\Debug options:
191 \\ --verbose-ast Dump produced AST to stdout
192 \\ --verbose-pp Dump preprocessor state
193 \\ --verbose-ir Dump ir to stdout
194 \\ --verbose-linker-args Dump linker args to stdout
195 \\
196 \\
197;
198
199/// Process command line arguments, returns true if something was written to std_out.
200pub fn parseArgs(
201 d: *Driver,
202 std_out: anytype,
203 macro_buf: anytype,
204 args: []const []const u8,
205) !bool {
206 var i: usize = 1;
207 var comment_arg: []const u8 = "";
208 var hosted: ?bool = null;
209 var gnuc_version: []const u8 = "4.2.1"; // default value set by clang
210 while (i < args.len) : (i += 1) {
211 const arg = args[i];
212 if (mem.startsWith(u8, arg, "-") and arg.len > 1) {
213 if (mem.eql(u8, arg, "-h") or mem.eql(u8, arg, "--help")) {
214 std_out.print(usage, .{args[0]}) catch |er| {
215 return d.fatal("unable to print usage: {s}", .{errorDescription(er)});
216 };
217 return true;
218 } else if (mem.eql(u8, arg, "-v") or mem.eql(u8, arg, "--version")) {
219 std_out.writeAll(@import("../backend.zig").version_str ++ "\n") catch |er| {
220 return d.fatal("unable to print version: {s}", .{errorDescription(er)});
221 };
222 return true;
223 } else if (mem.startsWith(u8, arg, "-D")) {
224 var macro = arg["-D".len..];
225 if (macro.len == 0) {
226 i += 1;
227 if (i >= args.len) {
228 try d.err("expected argument after -I");
229 continue;
230 }
231 macro = args[i];
232 }
233 var value: []const u8 = "1";
234 if (mem.indexOfScalar(u8, macro, '=')) |some| {
235 value = macro[some + 1 ..];
236 macro = macro[0..some];
237 }
238 try macro_buf.print("#define {s} {s}\n", .{ macro, value });
239 } else if (mem.startsWith(u8, arg, "-U")) {
240 var macro = arg["-U".len..];
241 if (macro.len == 0) {
242 i += 1;
243 if (i >= args.len) {
244 try d.err("expected argument after -I");
245 continue;
246 }
247 macro = args[i];
248 }
249 try macro_buf.print("#undef {s}\n", .{macro});
250 } else if (mem.eql(u8, arg, "-undef")) {
251 d.system_defines = .no_system_defines;
252 } else if (mem.eql(u8, arg, "-c") or mem.eql(u8, arg, "--compile")) {
253 d.only_compile = true;
254 } else if (mem.eql(u8, arg, "-dD")) {
255 d.debug_dump_letters.d = true;
256 } else if (mem.eql(u8, arg, "-dM")) {
257 d.debug_dump_letters.m = true;
258 } else if (mem.eql(u8, arg, "-dN")) {
259 d.debug_dump_letters.n = true;
260 } else if (mem.eql(u8, arg, "-E")) {
261 d.only_preprocess = true;
262 } else if (mem.eql(u8, arg, "-P") or mem.eql(u8, arg, "--no-line-commands")) {
263 d.line_commands = false;
264 } else if (mem.eql(u8, arg, "-fuse-line-directives")) {
265 d.use_line_directives = true;
266 } else if (mem.eql(u8, arg, "-fno-use-line-directives")) {
267 d.use_line_directives = false;
268 } else if (mem.eql(u8, arg, "-fchar8_t")) {
269 d.comp.langopts.has_char8_t_override = true;
270 } else if (mem.eql(u8, arg, "-fno-char8_t")) {
271 d.comp.langopts.has_char8_t_override = false;
272 } else if (mem.eql(u8, arg, "-fcolor-diagnostics")) {
273 d.color = true;
274 } else if (mem.eql(u8, arg, "-fno-color-diagnostics")) {
275 d.color = false;
276 } else if (mem.eql(u8, arg, "-fdollars-in-identifiers")) {
277 d.comp.langopts.dollars_in_identifiers = true;
278 } else if (mem.eql(u8, arg, "-fno-dollars-in-identifiers")) {
279 d.comp.langopts.dollars_in_identifiers = false;
280 } else if (mem.eql(u8, arg, "-fdigraphs")) {
281 d.comp.langopts.digraphs = true;
282 } else if (mem.eql(u8, arg, "-fgnu-inline-asm")) {
283 d.comp.langopts.gnu_asm = true;
284 } else if (mem.eql(u8, arg, "-fno-gnu-inline-asm")) {
285 d.comp.langopts.gnu_asm = false;
286 } else if (mem.eql(u8, arg, "-fno-digraphs")) {
287 d.comp.langopts.digraphs = false;
288 } else if (option(arg, "-fmacro-backtrace-limit=")) |limit_str| {
289 var limit = std.fmt.parseInt(u32, limit_str, 10) catch {
290 try d.err("-fmacro-backtrace-limit takes a number argument");
291 continue;
292 };
293
294 if (limit == 0) limit = std.math.maxInt(u32);
295 d.comp.diagnostics.macro_backtrace_limit = limit;
296 } else if (mem.eql(u8, arg, "-fnative-half-type")) {
297 d.comp.langopts.use_native_half_type = true;
298 } else if (mem.eql(u8, arg, "-fnative-half-arguments-and-returns")) {
299 d.comp.langopts.allow_half_args_and_returns = true;
300 } else if (mem.eql(u8, arg, "-fshort-enums")) {
301 d.comp.langopts.short_enums = true;
302 } else if (mem.eql(u8, arg, "-fno-short-enums")) {
303 d.comp.langopts.short_enums = false;
304 } else if (mem.eql(u8, arg, "-fsigned-char")) {
305 d.comp.langopts.setCharSignedness(.signed);
306 } else if (mem.eql(u8, arg, "-fno-signed-char")) {
307 d.comp.langopts.setCharSignedness(.unsigned);
308 } else if (mem.eql(u8, arg, "-funsigned-char")) {
309 d.comp.langopts.setCharSignedness(.unsigned);
310 } else if (mem.eql(u8, arg, "-fno-unsigned-char")) {
311 d.comp.langopts.setCharSignedness(.signed);
312 } else if (mem.eql(u8, arg, "-fdeclspec")) {
313 d.comp.langopts.declspec_attrs = true;
314 } else if (mem.eql(u8, arg, "-fno-declspec")) {
315 d.comp.langopts.declspec_attrs = false;
316 } else if (mem.eql(u8, arg, "-ffreestanding")) {
317 hosted = false;
318 } else if (mem.eql(u8, arg, "-fhosted")) {
319 hosted = true;
320 } else if (mem.eql(u8, arg, "-fms-extensions")) {
321 d.comp.langopts.enableMSExtensions();
322 } else if (mem.eql(u8, arg, "-fno-ms-extensions")) {
323 d.comp.langopts.disableMSExtensions();
324 } else if (mem.startsWith(u8, arg, "-I")) {
325 var path = arg["-I".len..];
326 if (path.len == 0) {
327 i += 1;
328 if (i >= args.len) {
329 try d.err("expected argument after -I");
330 continue;
331 }
332 path = args[i];
333 }
334 try d.comp.include_dirs.append(d.comp.gpa, path);
335 } else if (mem.startsWith(u8, arg, "-fsyntax-only")) {
336 d.only_syntax = true;
337 } else if (mem.startsWith(u8, arg, "-fno-syntax-only")) {
338 d.only_syntax = false;
339 } else if (mem.eql(u8, arg, "-fgnuc-version=")) {
340 gnuc_version = "0";
341 } else if (option(arg, "-fgnuc-version=")) |version| {
342 gnuc_version = version;
343 } else if (mem.startsWith(u8, arg, "-isystem")) {
344 var path = arg["-isystem".len..];
345 if (path.len == 0) {
346 i += 1;
347 if (i >= args.len) {
348 try d.err("expected argument after -isystem");
349 continue;
350 }
351 path = args[i];
352 }
353 const duped = try d.comp.gpa.dupe(u8, path);
354 errdefer d.comp.gpa.free(duped);
355 try d.comp.system_include_dirs.append(d.comp.gpa, duped);
356 } else if (option(arg, "--emulate=")) |compiler_str| {
357 const compiler = std.meta.stringToEnum(LangOpts.Compiler, compiler_str) orelse {
358 try d.comp.addDiagnostic(.{ .tag = .cli_invalid_emulate, .extra = .{ .str = arg } }, &.{});
359 continue;
360 };
361 d.comp.langopts.setEmulatedCompiler(compiler);
362 } else if (option(arg, "-ffp-eval-method=")) |fp_method_str| {
363 const fp_eval_method = std.meta.stringToEnum(LangOpts.FPEvalMethod, fp_method_str) orelse .indeterminate;
364 if (fp_eval_method == .indeterminate) {
365 try d.comp.addDiagnostic(.{ .tag = .cli_invalid_fp_eval_method, .extra = .{ .str = fp_method_str } }, &.{});
366 continue;
367 }
368 d.comp.langopts.setFpEvalMethod(fp_eval_method);
369 } else if (mem.startsWith(u8, arg, "-o")) {
370 var file = arg["-o".len..];
371 if (file.len == 0) {
372 i += 1;
373 if (i >= args.len) {
374 try d.err("expected argument after -o");
375 continue;
376 }
377 file = args[i];
378 }
379 d.output_name = file;
380 } else if (option(arg, "--sysroot=")) |sysroot| {
381 d.sysroot = sysroot;
382 } else if (mem.eql(u8, arg, "-pedantic")) {
383 d.comp.diagnostics.options.pedantic = .warning;
384 } else if (option(arg, "--rtlib=")) |rtlib| {
385 if (mem.eql(u8, rtlib, "compiler-rt") or mem.eql(u8, rtlib, "libgcc") or mem.eql(u8, rtlib, "platform")) {
386 d.rtlib = rtlib;
387 } else {
388 try d.comp.addDiagnostic(.{ .tag = .invalid_rtlib, .extra = .{ .str = rtlib } }, &.{});
389 }
390 } else if (option(arg, "-Werror=")) |err_name| {
391 try d.comp.diagnostics.set(err_name, .@"error");
392 } else if (mem.eql(u8, arg, "-Wno-fatal-errors")) {
393 d.comp.diagnostics.fatal_errors = false;
394 } else if (option(arg, "-Wno-")) |err_name| {
395 try d.comp.diagnostics.set(err_name, .off);
396 } else if (mem.eql(u8, arg, "-Wfatal-errors")) {
397 d.comp.diagnostics.fatal_errors = true;
398 } else if (option(arg, "-W")) |err_name| {
399 try d.comp.diagnostics.set(err_name, .warning);
400 } else if (option(arg, "-std=")) |standard| {
401 d.comp.langopts.setStandard(standard) catch
402 try d.comp.addDiagnostic(.{ .tag = .cli_invalid_standard, .extra = .{ .str = arg } }, &.{});
403 } else if (mem.eql(u8, arg, "-S") or mem.eql(u8, arg, "--assemble")) {
404 d.only_preprocess_and_compile = true;
405 } else if (option(arg, "--target=")) |triple| {
406 const query = std.Target.Query.parse(.{ .arch_os_abi = triple }) catch {
407 try d.comp.addDiagnostic(.{ .tag = .cli_invalid_target, .extra = .{ .str = arg } }, &.{});
408 continue;
409 };
410 const target = std.zig.system.resolveTargetQuery(query) catch |e| {
411 return d.fatal("unable to resolve target: {s}", .{errorDescription(e)});
412 };
413 d.comp.target = target;
414 d.comp.langopts.setEmulatedCompiler(target_util.systemCompiler(target));
415 d.raw_target_triple = triple;
416 } else if (mem.eql(u8, arg, "--verbose-ast")) {
417 d.verbose_ast = true;
418 } else if (mem.eql(u8, arg, "--verbose-pp")) {
419 d.verbose_pp = true;
420 } else if (mem.eql(u8, arg, "--verbose-ir")) {
421 d.verbose_ir = true;
422 } else if (mem.eql(u8, arg, "--verbose-linker-args")) {
423 d.verbose_linker_args = true;
424 } else if (mem.eql(u8, arg, "-C") or mem.eql(u8, arg, "--comments")) {
425 d.comp.langopts.preserve_comments = true;
426 comment_arg = arg;
427 } else if (mem.eql(u8, arg, "-CC") or mem.eql(u8, arg, "--comments-in-macros")) {
428 d.comp.langopts.preserve_comments = true;
429 d.comp.langopts.preserve_comments_in_macros = true;
430 comment_arg = arg;
431 } else if (option(arg, "-fuse-ld=")) |linker_name| {
432 d.use_linker = linker_name;
433 } else if (mem.eql(u8, arg, "-fuse-ld=")) {
434 d.use_linker = null;
435 } else if (option(arg, "--ld-path=")) |linker_path| {
436 d.linker_path = linker_path;
437 } else if (mem.eql(u8, arg, "-r")) {
438 d.relocatable = true;
439 } else if (mem.eql(u8, arg, "-shared")) {
440 d.shared = true;
441 } else if (mem.eql(u8, arg, "-shared-libgcc")) {
442 d.shared_libgcc = true;
443 } else if (mem.eql(u8, arg, "-static")) {
444 d.static = true;
445 } else if (mem.eql(u8, arg, "-static-libgcc")) {
446 d.static_libgcc = true;
447 } else if (mem.eql(u8, arg, "-static-pie")) {
448 d.static_pie = true;
449 } else if (mem.eql(u8, arg, "-pie")) {
450 d.pie = true;
451 } else if (mem.eql(u8, arg, "-no-pie") or mem.eql(u8, arg, "-nopie")) {
452 d.pie = false;
453 } else if (mem.eql(u8, arg, "-rdynamic")) {
454 d.rdynamic = true;
455 } else if (mem.eql(u8, arg, "-s")) {
456 d.strip = true;
457 } else if (mem.eql(u8, arg, "-nodefaultlibs")) {
458 d.nodefaultlibs = true;
459 } else if (mem.eql(u8, arg, "-nolibc")) {
460 d.nolibc = true;
461 } else if (mem.eql(u8, arg, "-nobuiltininc")) {
462 d.nobuiltininc = true;
463 } else if (mem.eql(u8, arg, "-nostdinc") or mem.eql(u8, arg, "--no-standard-includes")) {
464 d.nostdinc = true;
465 } else if (mem.eql(u8, arg, "-nostdlibinc")) {
466 d.nostdlibinc = true;
467 } else if (mem.eql(u8, arg, "-nostdlib")) {
468 d.nostdlib = true;
469 } else if (mem.eql(u8, arg, "-nostartfiles")) {
470 d.nostartfiles = true;
471 } else if (option(arg, "--unwindlib=")) |unwindlib| {
472 const valid_unwindlibs: [5][]const u8 = .{ "", "none", "platform", "libunwind", "libgcc" };
473 for (valid_unwindlibs) |name| {
474 if (mem.eql(u8, name, unwindlib)) {
475 d.unwindlib = unwindlib;
476 break;
477 }
478 } else {
479 try d.comp.addDiagnostic(.{ .tag = .invalid_unwindlib, .extra = .{ .str = unwindlib } }, &.{});
480 }
481 } else {
482 try d.comp.addDiagnostic(.{ .tag = .cli_unknown_arg, .extra = .{ .str = arg } }, &.{});
483 }
484 } else if (std.mem.endsWith(u8, arg, ".o") or std.mem.endsWith(u8, arg, ".obj")) {
485 try d.link_objects.append(d.comp.gpa, arg);
486 } else {
487 const source = d.addSource(arg) catch |er| {
488 return d.fatal("unable to add source file '{s}': {s}", .{ arg, errorDescription(er) });
489 };
490 try d.inputs.append(d.comp.gpa, source);
491 }
492 }
493 if (d.comp.langopts.preserve_comments and !d.only_preprocess) {
494 return d.fatal("invalid argument '{s}' only allowed with '-E'", .{comment_arg});
495 }
496 if (hosted) |is_hosted| {
497 if (is_hosted) {
498 if (d.comp.target.os.tag == .freestanding) {
499 return d.fatal("Cannot use freestanding target with `-fhosted`", .{});
500 }
501 } else {
502 d.comp.target.os.tag = .freestanding;
503 }
504 }
505 const version = GCCVersion.parse(gnuc_version);
506 if (version.major == -1) {
507 return d.fatal("invalid value '{0s}' in '-fgnuc-version={0s}'", .{gnuc_version});
508 }
509 d.comp.langopts.gnuc_version = version.toUnsigned();
510 return false;
511}
512
513fn option(arg: []const u8, name: []const u8) ?[]const u8 {
514 if (std.mem.startsWith(u8, arg, name) and arg.len > name.len) {
515 return arg[name.len..];
516 }
517 return null;
518}
519
520fn addSource(d: *Driver, path: []const u8) !Source {
521 if (mem.eql(u8, "-", path)) {
522 const stdin = std.io.getStdIn().reader();
523 const input = try stdin.readAllAlloc(d.comp.gpa, std.math.maxInt(u32));
524 defer d.comp.gpa.free(input);
525 return d.comp.addSourceFromBuffer("<stdin>", input);
526 }
527 return d.comp.addSourceFromPath(path);
528}
529
530pub fn err(d: *Driver, msg: []const u8) !void {
531 try d.comp.addDiagnostic(.{ .tag = .cli_error, .extra = .{ .str = msg } }, &.{});
532}
533
534pub fn fatal(d: *Driver, comptime fmt: []const u8, args: anytype) error{ FatalError, OutOfMemory } {
535 try d.comp.diagnostics.list.append(d.comp.gpa, .{
536 .tag = .cli_error,
537 .kind = .@"fatal error",
538 .extra = .{ .str = try std.fmt.allocPrint(d.comp.diagnostics.arena.allocator(), fmt, args) },
539 });
540 return error.FatalError;
541}
542
543pub fn renderErrors(d: *Driver) void {
544 Diagnostics.render(d.comp, d.detectConfig(std.io.getStdErr()));
545}
546
547pub fn detectConfig(d: *Driver, file: std.fs.File) std.io.tty.Config {
548 if (d.color == true) return .escape_codes;
549 if (d.color == false) return .no_color;
550
551 if (file.supportsAnsiEscapeCodes()) return .escape_codes;
552 if (@import("builtin").os.tag == .windows and file.isTty()) {
553 var info: std.os.windows.CONSOLE_SCREEN_BUFFER_INFO = undefined;
554 if (std.os.windows.kernel32.GetConsoleScreenBufferInfo(file.handle, &info) != std.os.windows.TRUE) {
555 return .no_color;
556 }
557 return .{ .windows_api = .{
558 .handle = file.handle,
559 .reset_attributes = info.wAttributes,
560 } };
561 }
562
563 return .no_color;
564}
565
566pub fn errorDescription(e: anyerror) []const u8 {
567 return switch (e) {
568 error.OutOfMemory => "ran out of memory",
569 error.FileNotFound => "file not found",
570 error.IsDir => "is a directory",
571 error.NotDir => "is not a directory",
572 error.NotOpenForReading => "file is not open for reading",
573 error.NotOpenForWriting => "file is not open for writing",
574 error.InvalidUtf8 => "path is not valid UTF-8",
575 error.InvalidWtf8 => "path is not valid WTF-8",
576 error.FileBusy => "file is busy",
577 error.NameTooLong => "file name is too long",
578 error.AccessDenied => "access denied",
579 error.FileTooBig => "file is too big",
580 error.ProcessFdQuotaExceeded, error.SystemFdQuotaExceeded => "ran out of file descriptors",
581 error.SystemResources => "ran out of system resources",
582 error.FatalError => "a fatal error occurred",
583 error.Unexpected => "an unexpected error occurred",
584 else => @errorName(e),
585 };
586}
587
588/// The entry point of the Aro compiler.
589/// **MAY call `exit` if `fast_exit` is set.**
590pub fn main(d: *Driver, tc: *Toolchain, args: []const []const u8, comptime fast_exit: bool) !void {
591 var macro_buf = std.ArrayList(u8).init(d.comp.gpa);
592 defer macro_buf.deinit();
593
594 const std_out = std.io.getStdOut().writer();
595 if (try parseArgs(d, std_out, macro_buf.writer(), args)) return;
596
597 const linking = !(d.only_preprocess or d.only_syntax or d.only_compile or d.only_preprocess_and_compile);
598
599 if (d.inputs.items.len == 0) {
600 return d.fatal("no input files", .{});
601 } else if (d.inputs.items.len != 1 and d.output_name != null and !linking) {
602 return d.fatal("cannot specify -o when generating multiple output files", .{});
603 }
604
605 if (!linking) for (d.link_objects.items) |obj| {
606 try d.comp.addDiagnostic(.{ .tag = .cli_unused_link_object, .extra = .{ .str = obj } }, &.{});
607 };
608
609 try tc.discover();
610 tc.defineSystemIncludes() catch |er| switch (er) {
611 error.OutOfMemory => return error.OutOfMemory,
612 error.AroIncludeNotFound => return d.fatal("unable to find Aro builtin headers", .{}),
613 };
614
615 const builtin = try d.comp.generateBuiltinMacros(d.system_defines);
616 const user_macros = try d.comp.addSourceFromBuffer("<command line>", macro_buf.items);
617
618 if (fast_exit and d.inputs.items.len == 1) {
619 d.processSource(tc, d.inputs.items[0], builtin, user_macros, fast_exit) catch |e| switch (e) {
620 error.FatalError => {
621 d.renderErrors();
622 d.exitWithCleanup(1);
623 },
624 else => |er| return er,
625 };
626 unreachable;
627 }
628
629 for (d.inputs.items) |source| {
630 d.processSource(tc, source, builtin, user_macros, fast_exit) catch |e| switch (e) {
631 error.FatalError => {
632 d.renderErrors();
633 },
634 else => |er| return er,
635 };
636 }
637 if (d.comp.diagnostics.errors != 0) {
638 if (fast_exit) d.exitWithCleanup(1);
639 return;
640 }
641 if (linking) {
642 try d.invokeLinker(tc, fast_exit);
643 }
644 if (fast_exit) std.process.exit(0);
645}
646
647fn processSource(
648 d: *Driver,
649 tc: *Toolchain,
650 source: Source,
651 builtin: Source,
652 user_macros: Source,
653 comptime fast_exit: bool,
654) !void {
655 d.comp.generated_buf.items.len = 0;
656 var pp = try Preprocessor.initDefault(d.comp);
657 defer pp.deinit();
658
659 if (d.comp.langopts.ms_extensions) {
660 d.comp.ms_cwd_source_id = source.id;
661 }
662 const dump_mode = d.debug_dump_letters.getPreprocessorDumpMode();
663 if (d.verbose_pp) pp.verbose = true;
664 if (d.only_preprocess) {
665 pp.preserve_whitespace = true;
666 if (d.line_commands) {
667 pp.linemarkers = if (d.use_line_directives) .line_directives else .numeric_directives;
668 }
669 switch (dump_mode) {
670 .macros_and_result, .macro_names_and_result => pp.store_macro_tokens = true,
671 .result_only, .macros_only => {},
672 }
673 }
674
675 try pp.preprocessSources(&.{ source, builtin, user_macros });
676
677 if (d.only_preprocess) {
678 d.renderErrors();
679
680 if (d.comp.diagnostics.errors != 0) {
681 if (fast_exit) std.process.exit(1); // Not linking, no need for cleanup.
682 return;
683 }
684
685 const file = if (d.output_name) |some|
686 std.fs.cwd().createFile(some, .{}) catch |er|
687 return d.fatal("unable to create output file '{s}': {s}", .{ some, errorDescription(er) })
688 else
689 std.io.getStdOut();
690 defer if (d.output_name != null) file.close();
691
692 var buf_w = std.io.bufferedWriter(file.writer());
693
694 pp.prettyPrintTokens(buf_w.writer(), dump_mode) catch |er|
695 return d.fatal("unable to write result: {s}", .{errorDescription(er)});
696
697 buf_w.flush() catch |er|
698 return d.fatal("unable to write result: {s}", .{errorDescription(er)});
699 if (fast_exit) std.process.exit(0); // Not linking, no need for cleanup.
700 return;
701 }
702
703 var tree = try pp.parse();
704 defer tree.deinit();
705
706 if (d.verbose_ast) {
707 const stdout = std.io.getStdOut();
708 var buf_writer = std.io.bufferedWriter(stdout.writer());
709 tree.dump(d.detectConfig(stdout), buf_writer.writer()) catch {};
710 buf_writer.flush() catch {};
711 }
712
713 const prev_errors = d.comp.diagnostics.errors;
714 d.renderErrors();
715
716 if (d.comp.diagnostics.errors != prev_errors) {
717 if (fast_exit) d.exitWithCleanup(1);
718 return; // do not compile if there were errors
719 }
720
721 if (d.only_syntax) {
722 if (fast_exit) std.process.exit(0); // Not linking, no need for cleanup.
723 return;
724 }
725
726 if (d.comp.target.ofmt != .elf or d.comp.target.cpu.arch != .x86_64) {
727 return d.fatal(
728 "unsupported target {s}-{s}-{s}, currently only x86-64 elf is supported",
729 .{ @tagName(d.comp.target.cpu.arch), @tagName(d.comp.target.os.tag), @tagName(d.comp.target.abi) },
730 );
731 }
732
733 var ir = try tree.genIr();
734 defer ir.deinit(d.comp.gpa);
735
736 if (d.verbose_ir) {
737 const stdout = std.io.getStdOut();
738 var buf_writer = std.io.bufferedWriter(stdout.writer());
739 ir.dump(d.comp.gpa, d.detectConfig(stdout), buf_writer.writer()) catch {};
740 buf_writer.flush() catch {};
741 }
742
743 var render_errors: Ir.Renderer.ErrorList = .{};
744 defer {
745 for (render_errors.values()) |msg| d.comp.gpa.free(msg);
746 render_errors.deinit(d.comp.gpa);
747 }
748
749 var obj = ir.render(d.comp.gpa, d.comp.target, &render_errors) catch |e| switch (e) {
750 error.OutOfMemory => return error.OutOfMemory,
751 error.LowerFail => {
752 return d.fatal(
753 "unable to render Ir to machine code: {s}",
754 .{render_errors.values()[0]},
755 );
756 },
757 };
758 defer obj.deinit();
759
760 // If it's used, name_buf will either hold a filename or `/tmp/<12 random bytes with base-64 encoding>.<extension>`
761 // both of which should fit into max_name_bytes for all systems
762 var name_buf: [std.fs.max_name_bytes]u8 = undefined;
763
764 const out_file_name = if (d.only_compile) blk: {
765 const fmt_template = "{s}{s}";
766 const fmt_args = .{
767 std.fs.path.stem(source.path),
768 d.comp.target.ofmt.fileExt(d.comp.target.cpu.arch),
769 };
770 break :blk d.output_name orelse
771 std.fmt.bufPrint(&name_buf, fmt_template, fmt_args) catch return d.fatal("Filename too long for filesystem: " ++ fmt_template, fmt_args);
772 } else blk: {
773 const random_bytes_count = 12;
774 const sub_path_len = comptime std.fs.base64_encoder.calcSize(random_bytes_count);
775
776 var random_bytes: [random_bytes_count]u8 = undefined;
777 std.crypto.random.bytes(&random_bytes);
778 var random_name: [sub_path_len]u8 = undefined;
779 _ = std.fs.base64_encoder.encode(&random_name, &random_bytes);
780
781 const fmt_template = "/tmp/{s}{s}";
782 const fmt_args = .{
783 random_name,
784 d.comp.target.ofmt.fileExt(d.comp.target.cpu.arch),
785 };
786 break :blk std.fmt.bufPrint(&name_buf, fmt_template, fmt_args) catch return d.fatal("Filename too long for filesystem: " ++ fmt_template, fmt_args);
787 };
788
789 const out_file = std.fs.cwd().createFile(out_file_name, .{}) catch |er|
790 return d.fatal("unable to create output file '{s}': {s}", .{ out_file_name, errorDescription(er) });
791 defer out_file.close();
792
793 obj.finish(out_file) catch |er|
794 return d.fatal("could not output to object file '{s}': {s}", .{ out_file_name, errorDescription(er) });
795
796 if (d.only_compile) {
797 if (fast_exit) std.process.exit(0); // Not linking, no need for cleanup.
798 return;
799 }
800 try d.link_objects.ensureUnusedCapacity(d.comp.gpa, 1);
801 d.link_objects.appendAssumeCapacity(try d.comp.gpa.dupe(u8, out_file_name));
802 d.temp_file_count += 1;
803 if (fast_exit) {
804 try d.invokeLinker(tc, fast_exit);
805 }
806}
807
808fn dumpLinkerArgs(items: []const []const u8) !void {
809 const stdout = std.io.getStdOut().writer();
810 for (items, 0..) |item, i| {
811 if (i > 0) try stdout.writeByte(' ');
812 try stdout.print("\"{}\"", .{std.zig.fmtEscapes(item)});
813 }
814 try stdout.writeByte('\n');
815}
816
817/// The entry point of the Aro compiler.
818/// **MAY call `exit` if `fast_exit` is set.**
819pub fn invokeLinker(d: *Driver, tc: *Toolchain, comptime fast_exit: bool) !void {
820 var argv = std.ArrayList([]const u8).init(d.comp.gpa);
821 defer argv.deinit();
822
823 var linker_path_buf: [std.fs.max_path_bytes]u8 = undefined;
824 const linker_path = try tc.getLinkerPath(&linker_path_buf);
825 try argv.append(linker_path);
826
827 try tc.buildLinkerArgs(&argv);
828
829 if (d.verbose_linker_args) {
830 dumpLinkerArgs(argv.items) catch |er| {
831 return d.fatal("unable to dump linker args: {s}", .{errorDescription(er)});
832 };
833 }
834 var child = std.process.Child.init(argv.items, d.comp.gpa);
835 // TODO handle better
836 child.stdin_behavior = .Inherit;
837 child.stdout_behavior = .Inherit;
838 child.stderr_behavior = .Inherit;
839
840 const term = child.spawnAndWait() catch |er| {
841 return d.fatal("unable to spawn linker: {s}", .{errorDescription(er)});
842 };
843 switch (term) {
844 .Exited => |code| if (code != 0) {
845 const e = d.fatal("linker exited with an error code", .{});
846 if (fast_exit) d.exitWithCleanup(code);
847 return e;
848 },
849 else => {
850 const e = d.fatal("linker crashed", .{});
851 if (fast_exit) d.exitWithCleanup(1);
852 return e;
853 },
854 }
855 if (fast_exit) d.exitWithCleanup(0);
856}
857
858fn exitWithCleanup(d: *Driver, code: u8) noreturn {
859 for (d.link_objects.items[d.link_objects.items.len - d.temp_file_count ..]) |obj| {
860 std.fs.deleteFileAbsolute(obj) catch {};
861 }
862 std.process.exit(code);
863}
lib/compiler/aro/aro/Driver/Distro.zig deleted-328
...@@ -1,328 +0,0 @@
1//! Tools for figuring out what Linux distro we're running on
2
3const std = @import("std");
4const mem = std.mem;
5const Filesystem = @import("Filesystem.zig").Filesystem;
6
7const MAX_BYTES = 1024; // TODO: Can we assume 1024 bytes enough for the info we need?
8
9/// Value for linker `--hash-style=` argument
10pub const HashStyle = enum {
11 both,
12 gnu,
13};
14
15pub const Tag = enum {
16 alpine,
17 arch,
18 debian_lenny,
19 debian_squeeze,
20 debian_wheezy,
21 debian_jessie,
22 debian_stretch,
23 debian_buster,
24 debian_bullseye,
25 debian_bookworm,
26 debian_trixie,
27 exherbo,
28 rhel5,
29 rhel6,
30 rhel7,
31 fedora,
32 gentoo,
33 open_suse,
34 ubuntu_hardy,
35 ubuntu_intrepid,
36 ubuntu_jaunty,
37 ubuntu_karmic,
38 ubuntu_lucid,
39 ubuntu_maverick,
40 ubuntu_natty,
41 ubuntu_oneiric,
42 ubuntu_precise,
43 ubuntu_quantal,
44 ubuntu_raring,
45 ubuntu_saucy,
46 ubuntu_trusty,
47 ubuntu_utopic,
48 ubuntu_vivid,
49 ubuntu_wily,
50 ubuntu_xenial,
51 ubuntu_yakkety,
52 ubuntu_zesty,
53 ubuntu_artful,
54 ubuntu_bionic,
55 ubuntu_cosmic,
56 ubuntu_disco,
57 ubuntu_eoan,
58 ubuntu_focal,
59 ubuntu_groovy,
60 ubuntu_hirsute,
61 ubuntu_impish,
62 ubuntu_jammy,
63 ubuntu_kinetic,
64 ubuntu_lunar,
65 unknown,
66
67 pub fn getHashStyle(self: Tag) HashStyle {
68 if (self.isOpenSUSE()) return .both;
69 return switch (self) {
70 .ubuntu_lucid,
71 .ubuntu_jaunty,
72 .ubuntu_karmic,
73 => .both,
74 else => .gnu,
75 };
76 }
77
78 pub fn isRedhat(self: Tag) bool {
79 return switch (self) {
80 .fedora,
81 .rhel5,
82 .rhel6,
83 .rhel7,
84 => true,
85 else => false,
86 };
87 }
88
89 pub fn isOpenSUSE(self: Tag) bool {
90 return self == .open_suse;
91 }
92
93 pub fn isDebian(self: Tag) bool {
94 return switch (self) {
95 .debian_lenny,
96 .debian_squeeze,
97 .debian_wheezy,
98 .debian_jessie,
99 .debian_stretch,
100 .debian_buster,
101 .debian_bullseye,
102 .debian_bookworm,
103 .debian_trixie,
104 => true,
105 else => false,
106 };
107 }
108 pub fn isUbuntu(self: Tag) bool {
109 return switch (self) {
110 .ubuntu_hardy,
111 .ubuntu_intrepid,
112 .ubuntu_jaunty,
113 .ubuntu_karmic,
114 .ubuntu_lucid,
115 .ubuntu_maverick,
116 .ubuntu_natty,
117 .ubuntu_oneiric,
118 .ubuntu_precise,
119 .ubuntu_quantal,
120 .ubuntu_raring,
121 .ubuntu_saucy,
122 .ubuntu_trusty,
123 .ubuntu_utopic,
124 .ubuntu_vivid,
125 .ubuntu_wily,
126 .ubuntu_xenial,
127 .ubuntu_yakkety,
128 .ubuntu_zesty,
129 .ubuntu_artful,
130 .ubuntu_bionic,
131 .ubuntu_cosmic,
132 .ubuntu_disco,
133 .ubuntu_eoan,
134 .ubuntu_focal,
135 .ubuntu_groovy,
136 .ubuntu_hirsute,
137 .ubuntu_impish,
138 .ubuntu_jammy,
139 .ubuntu_kinetic,
140 .ubuntu_lunar,
141 => true,
142
143 else => false,
144 };
145 }
146 pub fn isAlpine(self: Tag) bool {
147 return self == .alpine;
148 }
149 pub fn isGentoo(self: Tag) bool {
150 return self == .gentoo;
151 }
152};
153
154fn scanForOsRelease(buf: []const u8) ?Tag {
155 var it = mem.splitScalar(u8, buf, '\n');
156 while (it.next()) |line| {
157 if (mem.startsWith(u8, line, "ID=")) {
158 const rest = line["ID=".len..];
159 if (mem.eql(u8, rest, "alpine")) return .alpine;
160 if (mem.eql(u8, rest, "fedora")) return .fedora;
161 if (mem.eql(u8, rest, "gentoo")) return .gentoo;
162 if (mem.eql(u8, rest, "arch")) return .arch;
163 if (mem.eql(u8, rest, "sles")) return .open_suse;
164 if (mem.eql(u8, rest, "opensuse")) return .open_suse;
165 if (mem.eql(u8, rest, "exherbo")) return .exherbo;
166 }
167 }
168 return null;
169}
170
171fn detectOsRelease(fs: Filesystem) ?Tag {
172 var buf: [MAX_BYTES]u8 = undefined;
173 const data = fs.readFile("/etc/os-release", &buf) orelse fs.readFile("/usr/lib/os-release", &buf) orelse return null;
174 return scanForOsRelease(data);
175}
176
177fn scanForLSBRelease(buf: []const u8) ?Tag {
178 var it = mem.splitScalar(u8, buf, '\n');
179 while (it.next()) |line| {
180 if (mem.startsWith(u8, line, "DISTRIB_CODENAME=")) {
181 const rest = line["DISTRIB_CODENAME=".len..];
182 if (mem.eql(u8, rest, "hardy")) return .ubuntu_hardy;
183 if (mem.eql(u8, rest, "intrepid")) return .ubuntu_intrepid;
184 if (mem.eql(u8, rest, "jaunty")) return .ubuntu_jaunty;
185 if (mem.eql(u8, rest, "karmic")) return .ubuntu_karmic;
186 if (mem.eql(u8, rest, "lucid")) return .ubuntu_lucid;
187 if (mem.eql(u8, rest, "maverick")) return .ubuntu_maverick;
188 if (mem.eql(u8, rest, "natty")) return .ubuntu_natty;
189 if (mem.eql(u8, rest, "oneiric")) return .ubuntu_oneiric;
190 if (mem.eql(u8, rest, "precise")) return .ubuntu_precise;
191 if (mem.eql(u8, rest, "quantal")) return .ubuntu_quantal;
192 if (mem.eql(u8, rest, "raring")) return .ubuntu_raring;
193 if (mem.eql(u8, rest, "saucy")) return .ubuntu_saucy;
194 if (mem.eql(u8, rest, "trusty")) return .ubuntu_trusty;
195 if (mem.eql(u8, rest, "utopic")) return .ubuntu_utopic;
196 if (mem.eql(u8, rest, "vivid")) return .ubuntu_vivid;
197 if (mem.eql(u8, rest, "wily")) return .ubuntu_wily;
198 if (mem.eql(u8, rest, "xenial")) return .ubuntu_xenial;
199 if (mem.eql(u8, rest, "yakkety")) return .ubuntu_yakkety;
200 if (mem.eql(u8, rest, "zesty")) return .ubuntu_zesty;
201 if (mem.eql(u8, rest, "artful")) return .ubuntu_artful;
202 if (mem.eql(u8, rest, "bionic")) return .ubuntu_bionic;
203 if (mem.eql(u8, rest, "cosmic")) return .ubuntu_cosmic;
204 if (mem.eql(u8, rest, "disco")) return .ubuntu_disco;
205 if (mem.eql(u8, rest, "eoan")) return .ubuntu_eoan;
206 if (mem.eql(u8, rest, "focal")) return .ubuntu_focal;
207 if (mem.eql(u8, rest, "groovy")) return .ubuntu_groovy;
208 if (mem.eql(u8, rest, "hirsute")) return .ubuntu_hirsute;
209 if (mem.eql(u8, rest, "impish")) return .ubuntu_impish;
210 if (mem.eql(u8, rest, "jammy")) return .ubuntu_jammy;
211 if (mem.eql(u8, rest, "kinetic")) return .ubuntu_kinetic;
212 if (mem.eql(u8, rest, "lunar")) return .ubuntu_lunar;
213 }
214 }
215 return null;
216}
217
218fn detectLSBRelease(fs: Filesystem) ?Tag {
219 var buf: [MAX_BYTES]u8 = undefined;
220 const data = fs.readFile("/etc/lsb-release", &buf) orelse return null;
221
222 return scanForLSBRelease(data);
223}
224
225fn scanForRedHat(buf: []const u8) Tag {
226 if (mem.startsWith(u8, buf, "Fedora release")) return .fedora;
227 if (mem.startsWith(u8, buf, "Red Hat Enterprise Linux") or mem.startsWith(u8, buf, "CentOS") or mem.startsWith(u8, buf, "Scientific Linux")) {
228 if (mem.indexOfPos(u8, buf, 0, "release 7") != null) return .rhel7;
229 if (mem.indexOfPos(u8, buf, 0, "release 6") != null) return .rhel6;
230 if (mem.indexOfPos(u8, buf, 0, "release 5") != null) return .rhel5;
231 }
232
233 return .unknown;
234}
235
236fn detectRedhat(fs: Filesystem) ?Tag {
237 var buf: [MAX_BYTES]u8 = undefined;
238 const data = fs.readFile("/etc/redhat-release", &buf) orelse return null;
239 return scanForRedHat(data);
240}
241
242fn scanForDebian(buf: []const u8) Tag {
243 var it = mem.splitScalar(u8, buf, '.');
244 if (std.fmt.parseInt(u8, it.next().?, 10)) |major| {
245 return switch (major) {
246 5 => .debian_lenny,
247 6 => .debian_squeeze,
248 7 => .debian_wheezy,
249 8 => .debian_jessie,
250 9 => .debian_stretch,
251 10 => .debian_buster,
252 11 => .debian_bullseye,
253 12 => .debian_bookworm,
254 13 => .debian_trixie,
255 else => .unknown,
256 };
257 } else |_| {}
258
259 it = mem.splitScalar(u8, buf, '\n');
260 const name = it.next().?;
261 if (mem.eql(u8, name, "squeeze/sid")) return .debian_squeeze;
262 if (mem.eql(u8, name, "wheezy/sid")) return .debian_wheezy;
263 if (mem.eql(u8, name, "jessie/sid")) return .debian_jessie;
264 if (mem.eql(u8, name, "stretch/sid")) return .debian_stretch;
265 if (mem.eql(u8, name, "buster/sid")) return .debian_buster;
266 if (mem.eql(u8, name, "bullseye/sid")) return .debian_bullseye;
267 if (mem.eql(u8, name, "bookworm/sid")) return .debian_bookworm;
268
269 return .unknown;
270}
271
272fn detectDebian(fs: Filesystem) ?Tag {
273 var buf: [MAX_BYTES]u8 = undefined;
274 const data = fs.readFile("/etc/debian_version", &buf) orelse return null;
275 return scanForDebian(data);
276}
277
278pub fn detect(target: std.Target, fs: Filesystem) Tag {
279 if (target.os.tag != .linux) return .unknown;
280
281 if (detectOsRelease(fs)) |tag| return tag;
282 if (detectLSBRelease(fs)) |tag| return tag;
283 if (detectRedhat(fs)) |tag| return tag;
284 if (detectDebian(fs)) |tag| return tag;
285
286 if (fs.exists("/etc/gentoo-release")) return .gentoo;
287
288 return .unknown;
289}
290
291test scanForDebian {
292 try std.testing.expectEqual(Tag.debian_squeeze, scanForDebian("squeeze/sid"));
293 try std.testing.expectEqual(Tag.debian_bullseye, scanForDebian("11.1.2"));
294 try std.testing.expectEqual(Tag.unknown, scanForDebian("None"));
295 try std.testing.expectEqual(Tag.unknown, scanForDebian(""));
296}
297
298test scanForRedHat {
299 try std.testing.expectEqual(Tag.fedora, scanForRedHat("Fedora release 7"));
300 try std.testing.expectEqual(Tag.rhel7, scanForRedHat("Red Hat Enterprise Linux release 7"));
301 try std.testing.expectEqual(Tag.rhel5, scanForRedHat("CentOS release 5"));
302 try std.testing.expectEqual(Tag.unknown, scanForRedHat("CentOS release 4"));
303 try std.testing.expectEqual(Tag.unknown, scanForRedHat(""));
304}
305
306test scanForLSBRelease {
307 const text =
308 \\DISTRIB_ID=Ubuntu
309 \\DISTRIB_RELEASE=20.04
310 \\DISTRIB_CODENAME=focal
311 \\DISTRIB_DESCRIPTION="Ubuntu 20.04.6 LTS"
312 \\
313 ;
314 try std.testing.expectEqual(Tag.ubuntu_focal, scanForLSBRelease(text).?);
315}
316
317test scanForOsRelease {
318 const text =
319 \\NAME="Alpine Linux"
320 \\ID=alpine
321 \\VERSION_ID=3.18.2
322 \\PRETTY_NAME="Alpine Linux v3.18"
323 \\HOME_URL="https://alpinelinux.org/"
324 \\BUG_REPORT_URL="https://gitlab.alpinelinux.org/alpine/aports/-/issues"
325 \\
326 ;
327 try std.testing.expectEqual(Tag.alpine, scanForOsRelease(text).?);
328}
lib/compiler/aro/aro/Driver/Filesystem.zig deleted-239
...@@ -1,239 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const builtin = @import("builtin");
4const is_windows = builtin.os.tag == .windows;
5
6fn readFileFake(entries: []const Filesystem.Entry, path: []const u8, buf: []u8) ?[]const u8 {
7 @branchHint(.cold);
8 for (entries) |entry| {
9 if (mem.eql(u8, entry.path, path)) {
10 const len = @min(entry.contents.len, buf.len);
11 @memcpy(buf[0..len], entry.contents[0..len]);
12 return buf[0..len];
13 }
14 }
15 return null;
16}
17
18fn findProgramByNameFake(entries: []const Filesystem.Entry, name: []const u8, path: ?[]const u8, buf: []u8) ?[]const u8 {
19 @branchHint(.cold);
20 if (mem.indexOfScalar(u8, name, '/') != null) {
21 @memcpy(buf[0..name.len], name);
22 return buf[0..name.len];
23 }
24 const path_env = path orelse return null;
25 var fib = std.heap.FixedBufferAllocator.init(buf);
26
27 var it = mem.tokenizeScalar(u8, path_env, std.fs.path.delimiter);
28 while (it.next()) |path_dir| {
29 defer fib.reset();
30 const full_path = std.fs.path.join(fib.allocator(), &.{ path_dir, name }) catch continue;
31 if (canExecuteFake(entries, full_path)) return full_path;
32 }
33
34 return null;
35}
36
37fn canExecuteFake(entries: []const Filesystem.Entry, path: []const u8) bool {
38 @branchHint(.cold);
39 for (entries) |entry| {
40 if (mem.eql(u8, entry.path, path)) {
41 return entry.executable;
42 }
43 }
44 return false;
45}
46
47fn existsFake(entries: []const Filesystem.Entry, path: []const u8) bool {
48 @branchHint(.cold);
49 var buf: [std.fs.max_path_bytes]u8 = undefined;
50 var fib = std.heap.FixedBufferAllocator.init(&buf);
51 const resolved = std.fs.path.resolvePosix(fib.allocator(), &.{path}) catch return false;
52 for (entries) |entry| {
53 if (mem.eql(u8, entry.path, resolved)) return true;
54 }
55 return false;
56}
57
58fn canExecutePosix(path: []const u8) bool {
59 std.posix.access(path, std.posix.X_OK) catch return false;
60 // Todo: ensure path is not a directory
61 return true;
62}
63
64/// TODO
65fn canExecuteWindows(path: []const u8) bool {
66 _ = path;
67 return true;
68}
69
70/// TODO
71fn findProgramByNameWindows(allocator: std.mem.Allocator, name: []const u8, path: ?[]const u8, buf: []u8) ?[]const u8 {
72 _ = path;
73 _ = buf;
74 _ = name;
75 _ = allocator;
76 return null;
77}
78
79/// TODO: does WASI need special handling?
80fn findProgramByNamePosix(name: []const u8, path: ?[]const u8, buf: []u8) ?[]const u8 {
81 if (mem.indexOfScalar(u8, name, '/') != null) {
82 @memcpy(buf[0..name.len], name);
83 return buf[0..name.len];
84 }
85 const path_env = path orelse return null;
86 var fib = std.heap.FixedBufferAllocator.init(buf);
87
88 var it = mem.tokenizeScalar(u8, path_env, std.fs.path.delimiter);
89 while (it.next()) |path_dir| {
90 defer fib.reset();
91 const full_path = std.fs.path.join(fib.allocator(), &.{ path_dir, name }) catch continue;
92 if (canExecutePosix(full_path)) return full_path;
93 }
94
95 return null;
96}
97
98pub const Filesystem = union(enum) {
99 real: void,
100 fake: []const Entry,
101
102 const Entry = struct {
103 path: []const u8,
104 contents: []const u8 = "",
105 executable: bool = false,
106 };
107
108 const FakeDir = struct {
109 entries: []const Entry,
110 path: []const u8,
111
112 fn iterate(self: FakeDir) FakeDir.Iterator {
113 return .{
114 .entries = self.entries,
115 .base = self.path,
116 };
117 }
118
119 const Iterator = struct {
120 entries: []const Entry,
121 base: []const u8,
122 i: usize = 0,
123
124 fn next(self: *@This()) !?std.fs.Dir.Entry {
125 while (self.i < self.entries.len) {
126 const entry = self.entries[self.i];
127 self.i += 1;
128 if (entry.path.len == self.base.len) continue;
129 if (std.mem.startsWith(u8, entry.path, self.base)) {
130 const remaining = entry.path[self.base.len + 1 ..];
131 if (std.mem.indexOfScalar(u8, remaining, std.fs.path.sep) != null) continue;
132 const extension = std.fs.path.extension(remaining);
133 const kind: std.fs.Dir.Entry.Kind = if (extension.len == 0) .directory else .file;
134 return .{ .name = remaining, .kind = kind };
135 }
136 }
137 return null;
138 }
139 };
140 };
141
142 const Dir = union(enum) {
143 dir: std.fs.Dir,
144 fake: FakeDir,
145
146 pub fn iterate(self: Dir) Iterator {
147 return switch (self) {
148 .dir => |dir| .{ .iterator = dir.iterate() },
149 .fake => |fake| .{ .fake = fake.iterate() },
150 };
151 }
152
153 pub fn close(self: *Dir) void {
154 switch (self.*) {
155 .dir => |*d| d.close(),
156 .fake => {},
157 }
158 }
159 };
160
161 const Iterator = union(enum) {
162 iterator: std.fs.Dir.Iterator,
163 fake: FakeDir.Iterator,
164
165 pub fn next(self: *Iterator) std.fs.Dir.Iterator.Error!?std.fs.Dir.Entry {
166 return switch (self.*) {
167 .iterator => |*it| it.next(),
168 .fake => |*it| it.next(),
169 };
170 }
171 };
172
173 pub fn exists(fs: Filesystem, path: []const u8) bool {
174 switch (fs) {
175 .real => {
176 std.fs.cwd().access(path, .{}) catch return false;
177 return true;
178 },
179 .fake => |paths| return existsFake(paths, path),
180 }
181 }
182
183 pub fn joinedExists(fs: Filesystem, parts: []const []const u8) bool {
184 var buf: [std.fs.max_path_bytes]u8 = undefined;
185 var fib = std.heap.FixedBufferAllocator.init(&buf);
186 const joined = std.fs.path.join(fib.allocator(), parts) catch return false;
187 return fs.exists(joined);
188 }
189
190 pub fn canExecute(fs: Filesystem, path: []const u8) bool {
191 return switch (fs) {
192 .real => if (is_windows) canExecuteWindows(path) else canExecutePosix(path),
193 .fake => |entries| canExecuteFake(entries, path),
194 };
195 }
196
197 /// Search for an executable named `name` using platform-specific logic
198 /// If it's found, write the full path to `buf` and return a slice of it
199 /// Otherwise retun null
200 pub fn findProgramByName(fs: Filesystem, allocator: std.mem.Allocator, name: []const u8, path: ?[]const u8, buf: []u8) ?[]const u8 {
201 std.debug.assert(name.len > 0);
202 return switch (fs) {
203 .real => if (is_windows) findProgramByNameWindows(allocator, name, path, buf) else findProgramByNamePosix(name, path, buf),
204 .fake => |entries| findProgramByNameFake(entries, name, path, buf),
205 };
206 }
207
208 /// Read the file at `path` into `buf`.
209 /// Returns null if any errors are encountered
210 /// Otherwise returns a slice of `buf`. If the file is larger than `buf` partial contents are returned
211 pub fn readFile(fs: Filesystem, path: []const u8, buf: []u8) ?[]const u8 {
212 return switch (fs) {
213 .real => {
214 const file = std.fs.cwd().openFile(path, .{}) catch return null;
215 defer file.close();
216
217 const bytes_read = file.readAll(buf) catch return null;
218 return buf[0..bytes_read];
219 },
220 .fake => |entries| readFileFake(entries, path, buf),
221 };
222 }
223
224 pub fn openDir(fs: Filesystem, dir_name: []const u8) std.fs.Dir.OpenError!Dir {
225 return switch (fs) {
226 .real => .{ .dir = try std.fs.cwd().openDir(dir_name, .{ .access_sub_paths = false, .iterate = true }) },
227 .fake => |entries| .{ .fake = .{ .entries = entries, .path = dir_name } },
228 };
229 }
230};
231
232test "Fake filesystem" {
233 const fs: Filesystem = .{ .fake = &.{
234 .{ .path = "/usr/bin" },
235 } };
236 try std.testing.expect(fs.exists("/usr/bin"));
237 try std.testing.expect(fs.exists("/usr/bin/foo/.."));
238 try std.testing.expect(!fs.exists("/usr/bin/bar"));
239}
lib/compiler/aro/aro/Driver/GCCDetector.zig deleted-638
...@@ -1,638 +0,0 @@
1const std = @import("std");
2const Toolchain = @import("../Toolchain.zig");
3const target_util = @import("../target.zig");
4const system_defaults = @import("system_defaults");
5const GCCVersion = @import("GCCVersion.zig");
6const Multilib = @import("Multilib.zig");
7
8const GCCDetector = @This();
9
10is_valid: bool = false,
11install_path: []const u8 = "",
12parent_lib_path: []const u8 = "",
13version: GCCVersion = .{},
14gcc_triple: []const u8 = "",
15selected: Multilib = .{},
16biarch_sibling: ?Multilib = null,
17
18pub fn deinit(self: *GCCDetector) void {
19 if (!self.is_valid) return;
20}
21
22pub fn appendToolPath(self: *const GCCDetector, tc: *Toolchain) !void {
23 if (!self.is_valid) return;
24 return tc.addPathFromComponents(&.{
25 self.parent_lib_path,
26 "..",
27 self.gcc_triple,
28 "bin",
29 }, .program);
30}
31
32fn addDefaultGCCPrefixes(prefixes: *std.ArrayListUnmanaged([]const u8), tc: *const Toolchain) !void {
33 const sysroot = tc.getSysroot();
34 const target = tc.getTarget();
35 if (sysroot.len == 0 and target.os.tag == .linux and tc.filesystem.exists("/opt/rh")) {
36 prefixes.appendAssumeCapacity("/opt/rh/gcc-toolset-12/root/usr");
37 prefixes.appendAssumeCapacity("/opt/rh/gcc-toolset-11/root/usr");
38 prefixes.appendAssumeCapacity("/opt/rh/gcc-toolset-10/root/usr");
39 prefixes.appendAssumeCapacity("/opt/rh/devtoolset-12/root/usr");
40 prefixes.appendAssumeCapacity("/opt/rh/devtoolset-11/root/usr");
41 prefixes.appendAssumeCapacity("/opt/rh/devtoolset-10/root/usr");
42 prefixes.appendAssumeCapacity("/opt/rh/devtoolset-9/root/usr");
43 prefixes.appendAssumeCapacity("/opt/rh/devtoolset-8/root/usr");
44 prefixes.appendAssumeCapacity("/opt/rh/devtoolset-7/root/usr");
45 prefixes.appendAssumeCapacity("/opt/rh/devtoolset-6/root/usr");
46 prefixes.appendAssumeCapacity("/opt/rh/devtoolset-4/root/usr");
47 prefixes.appendAssumeCapacity("/opt/rh/devtoolset-3/root/usr");
48 prefixes.appendAssumeCapacity("/opt/rh/devtoolset-2/root/usr");
49 }
50 if (sysroot.len == 0) {
51 prefixes.appendAssumeCapacity("/usr");
52 } else {
53 var usr_path = try tc.arena.alloc(u8, 4 + sysroot.len);
54 @memcpy(usr_path[0..4], "/usr");
55 @memcpy(usr_path[4..], sysroot);
56 prefixes.appendAssumeCapacity(usr_path);
57 }
58}
59
60fn collectLibDirsAndTriples(
61 tc: *Toolchain,
62 lib_dirs: *std.ArrayListUnmanaged([]const u8),
63 triple_aliases: *std.ArrayListUnmanaged([]const u8),
64 biarch_libdirs: *std.ArrayListUnmanaged([]const u8),
65 biarch_triple_aliases: *std.ArrayListUnmanaged([]const u8),
66) !void {
67 const AArch64LibDirs: [2][]const u8 = .{ "/lib64", "/lib" };
68 const AArch64Triples: [4][]const u8 = .{ "aarch64-none-linux-gnu", "aarch64-linux-gnu", "aarch64-redhat-linux", "aarch64-suse-linux" };
69 const AArch64beLibDirs: [1][]const u8 = .{"/lib"};
70 const AArch64beTriples: [2][]const u8 = .{ "aarch64_be-none-linux-gnu", "aarch64_be-linux-gnu" };
71
72 const ARMLibDirs: [1][]const u8 = .{"/lib"};
73 const ARMTriples: [1][]const u8 = .{"arm-linux-gnueabi"};
74 const ARMHFTriples: [4][]const u8 = .{ "arm-linux-gnueabihf", "armv7hl-redhat-linux-gnueabi", "armv6hl-suse-linux-gnueabi", "armv7hl-suse-linux-gnueabi" };
75
76 const ARMebLibDirs: [1][]const u8 = .{"/lib"};
77 const ARMebTriples: [1][]const u8 = .{"armeb-linux-gnueabi"};
78 const ARMebHFTriples: [2][]const u8 = .{ "armeb-linux-gnueabihf", "armebv7hl-redhat-linux-gnueabi" };
79
80 const AVRLibDirs: [1][]const u8 = .{"/lib"};
81 const AVRTriples: [1][]const u8 = .{"avr"};
82
83 const CSKYLibDirs: [1][]const u8 = .{"/lib"};
84 const CSKYTriples: [3][]const u8 = .{ "csky-linux-gnuabiv2", "csky-linux-uclibcabiv2", "csky-elf-noneabiv2" };
85
86 const X86_64LibDirs: [2][]const u8 = .{ "/lib64", "/lib" };
87 const X86_64Triples: [11][]const u8 = .{
88 "x86_64-linux-gnu", "x86_64-unknown-linux-gnu",
89 "x86_64-pc-linux-gnu", "x86_64-redhat-linux6E",
90 "x86_64-redhat-linux", "x86_64-suse-linux",
91 "x86_64-manbo-linux-gnu", "x86_64-linux-gnu",
92 "x86_64-slackware-linux", "x86_64-unknown-linux",
93 "x86_64-amazon-linux",
94 };
95 const X32Triples: [2][]const u8 = .{ "x86_64-linux-gnux32", "x86_64-pc-linux-gnux32" };
96 const X32LibDirs: [2][]const u8 = .{ "/libx32", "/lib" };
97 const X86LibDirs: [2][]const u8 = .{ "/lib32", "/lib" };
98 const X86Triples: [9][]const u8 = .{
99 "i586-linux-gnu", "i686-linux-gnu", "i686-pc-linux-gnu",
100 "i386-redhat-linux6E", "i686-redhat-linux", "i386-redhat-linux",
101 "i586-suse-linux", "i686-montavista-linux", "i686-gnu",
102 };
103
104 const LoongArch64LibDirs: [2][]const u8 = .{ "/lib64", "/lib" };
105 const LoongArch64Triples: [2][]const u8 = .{ "loongarch64-linux-gnu", "loongarch64-unknown-linux-gnu" };
106
107 const M68kLibDirs: [1][]const u8 = .{"/lib"};
108 const M68kTriples: [3][]const u8 = .{ "m68k-linux-gnu", "m68k-unknown-linux-gnu", "m68k-suse-linux" };
109
110 const MIPSLibDirs: [2][]const u8 = .{ "/libo32", "/lib" };
111 const MIPSTriples: [5][]const u8 = .{
112 "mips-linux-gnu", "mips-mti-linux",
113 "mips-mti-linux-gnu", "mips-img-linux-gnu",
114 "mipsisa32r6-linux-gnu",
115 };
116 const MIPSELLibDirs: [2][]const u8 = .{ "/libo32", "/lib" };
117 const MIPSELTriples: [3][]const u8 = .{ "mipsel-linux-gnu", "mips-img-linux-gnu", "mipsisa32r6el-linux-gnu" };
118
119 const MIPS64LibDirs: [2][]const u8 = .{ "/lib64", "/lib" };
120 const MIPS64Triples: [6][]const u8 = .{
121 "mips64-linux-gnu", "mips-mti-linux-gnu",
122 "mips-img-linux-gnu", "mips64-linux-gnuabi64",
123 "mipsisa64r6-linux-gnu", "mipsisa64r6-linux-gnuabi64",
124 };
125 const MIPS64ELLibDirs: [2][]const u8 = .{ "/lib64", "/lib" };
126 const MIPS64ELTriples: [6][]const u8 = .{
127 "mips64el-linux-gnu", "mips-mti-linux-gnu",
128 "mips-img-linux-gnu", "mips64el-linux-gnuabi64",
129 "mipsisa64r6el-linux-gnu", "mipsisa64r6el-linux-gnuabi64",
130 };
131
132 const MIPSN32LibDirs: [1][]const u8 = .{"/lib32"};
133 const MIPSN32Triples: [2][]const u8 = .{ "mips64-linux-gnuabin32", "mipsisa64r6-linux-gnuabin32" };
134 const MIPSN32ELLibDirs: [1][]const u8 = .{"/lib32"};
135 const MIPSN32ELTriples: [2][]const u8 = .{ "mips64el-linux-gnuabin32", "mipsisa64r6el-linux-gnuabin32" };
136
137 const MSP430LibDirs: [1][]const u8 = .{"/lib"};
138 const MSP430Triples: [1][]const u8 = .{"msp430-elf"};
139
140 const PPCLibDirs: [2][]const u8 = .{ "/lib32", "/lib" };
141 const PPCTriples: [5][]const u8 = .{
142 "powerpc-linux-gnu", "powerpc-unknown-linux-gnu", "powerpc-linux-gnuspe",
143 // On 32-bit PowerPC systems running SUSE Linux, gcc is configured as a
144 // 64-bit compiler which defaults to "-m32", hence "powerpc64-suse-linux".
145 "powerpc64-suse-linux", "powerpc-montavista-linuxspe",
146 };
147 const PPCLELibDirs: [2][]const u8 = .{ "/lib32", "/lib" };
148 const PPCLETriples: [3][]const u8 = .{ "powerpcle-linux-gnu", "powerpcle-unknown-linux-gnu", "powerpcle-linux-musl" };
149
150 const PPC64LibDirs: [2][]const u8 = .{ "/lib64", "/lib" };
151 const PPC64Triples: [4][]const u8 = .{
152 "powerpc64-linux-gnu", "powerpc64-unknown-linux-gnu",
153 "powerpc64-suse-linux", "ppc64-redhat-linux",
154 };
155 const PPC64LELibDirs: [2][]const u8 = .{ "/lib64", "/lib" };
156 const PPC64LETriples: [5][]const u8 = .{
157 "powerpc64le-linux-gnu", "powerpc64le-unknown-linux-gnu",
158 "powerpc64le-none-linux-gnu", "powerpc64le-suse-linux",
159 "ppc64le-redhat-linux",
160 };
161
162 const RISCV32LibDirs: [2][]const u8 = .{ "/lib32", "/lib" };
163 const RISCV32Triples: [3][]const u8 = .{ "riscv32-unknown-linux-gnu", "riscv32-linux-gnu", "riscv32-unknown-elf" };
164 const RISCV64LibDirs: [2][]const u8 = .{ "/lib64", "/lib" };
165 const RISCV64Triples: [3][]const u8 = .{
166 "riscv64-unknown-linux-gnu",
167 "riscv64-linux-gnu",
168 "riscv64-unknown-elf",
169 };
170
171 const SPARCv8LibDirs: [2][]const u8 = .{ "/lib32", "/lib" };
172 const SPARCv8Triples: [2][]const u8 = .{ "sparc-linux-gnu", "sparcv8-linux-gnu" };
173 const SPARCv9LibDirs: [2][]const u8 = .{ "/lib64", "/lib" };
174 const SPARCv9Triples: [2][]const u8 = .{ "sparc64-linux-gnu", "sparcv9-linux-gnu" };
175
176 const SystemZLibDirs: [2][]const u8 = .{ "/lib64", "/lib" };
177 const SystemZTriples: [5][]const u8 = .{
178 "s390x-linux-gnu", "s390x-unknown-linux-gnu", "s390x-ibm-linux-gnu",
179 "s390x-suse-linux", "s390x-redhat-linux",
180 };
181 const target = tc.getTarget();
182 if (target.os.tag == .solaris) {
183 // TODO
184 return;
185 }
186 if (target.isAndroid()) {
187 const AArch64AndroidTriples: [1][]const u8 = .{"aarch64-linux-android"};
188 const ARMAndroidTriples: [1][]const u8 = .{"arm-linux-androideabi"};
189 const MIPSELAndroidTriples: [1][]const u8 = .{"mipsel-linux-android"};
190 const MIPS64ELAndroidTriples: [1][]const u8 = .{"mips64el-linux-android"};
191 const X86AndroidTriples: [1][]const u8 = .{"i686-linux-android"};
192 const X86_64AndroidTriples: [1][]const u8 = .{"x86_64-linux-android"};
193
194 switch (target.cpu.arch) {
195 .aarch64 => {
196 lib_dirs.appendSliceAssumeCapacity(&AArch64LibDirs);
197 triple_aliases.appendSliceAssumeCapacity(&AArch64AndroidTriples);
198 },
199 .arm,
200 .thumb,
201 => {
202 lib_dirs.appendSliceAssumeCapacity(&ARMLibDirs);
203 triple_aliases.appendSliceAssumeCapacity(&ARMAndroidTriples);
204 },
205 .mipsel => {
206 lib_dirs.appendSliceAssumeCapacity(&MIPSELLibDirs);
207 triple_aliases.appendSliceAssumeCapacity(&MIPSELAndroidTriples);
208 biarch_libdirs.appendSliceAssumeCapacity(&MIPS64ELLibDirs);
209 biarch_triple_aliases.appendSliceAssumeCapacity(&MIPS64ELAndroidTriples);
210 },
211 .mips64el => {
212 lib_dirs.appendSliceAssumeCapacity(&MIPS64ELLibDirs);
213 triple_aliases.appendSliceAssumeCapacity(&MIPS64ELAndroidTriples);
214 biarch_libdirs.appendSliceAssumeCapacity(&MIPSELLibDirs);
215 biarch_triple_aliases.appendSliceAssumeCapacity(&MIPSELAndroidTriples);
216 },
217 .x86_64 => {
218 lib_dirs.appendSliceAssumeCapacity(&X86_64LibDirs);
219 triple_aliases.appendSliceAssumeCapacity(&X86_64AndroidTriples);
220 biarch_libdirs.appendSliceAssumeCapacity(&X86LibDirs);
221 biarch_triple_aliases.appendSliceAssumeCapacity(&X86AndroidTriples);
222 },
223 .x86 => {
224 lib_dirs.appendSliceAssumeCapacity(&X86LibDirs);
225 triple_aliases.appendSliceAssumeCapacity(&X86AndroidTriples);
226 biarch_libdirs.appendSliceAssumeCapacity(&X86_64LibDirs);
227 biarch_triple_aliases.appendSliceAssumeCapacity(&X86_64AndroidTriples);
228 },
229 else => {},
230 }
231 return;
232 }
233 switch (target.cpu.arch) {
234 .aarch64 => {
235 lib_dirs.appendSliceAssumeCapacity(&AArch64LibDirs);
236 triple_aliases.appendSliceAssumeCapacity(&AArch64Triples);
237 biarch_libdirs.appendSliceAssumeCapacity(&AArch64LibDirs);
238 biarch_triple_aliases.appendSliceAssumeCapacity(&AArch64Triples);
239 },
240 .aarch64_be => {
241 lib_dirs.appendSliceAssumeCapacity(&AArch64beLibDirs);
242 triple_aliases.appendSliceAssumeCapacity(&AArch64beTriples);
243 biarch_libdirs.appendSliceAssumeCapacity(&AArch64beLibDirs);
244 biarch_triple_aliases.appendSliceAssumeCapacity(&AArch64beTriples);
245 },
246 .arm, .thumb => {
247 lib_dirs.appendSliceAssumeCapacity(&ARMLibDirs);
248 if (target.abi == .gnueabihf) {
249 triple_aliases.appendSliceAssumeCapacity(&ARMHFTriples);
250 } else {
251 triple_aliases.appendSliceAssumeCapacity(&ARMTriples);
252 }
253 },
254 .armeb, .thumbeb => {
255 lib_dirs.appendSliceAssumeCapacity(&ARMebLibDirs);
256 if (target.abi == .gnueabihf) {
257 triple_aliases.appendSliceAssumeCapacity(&ARMebHFTriples);
258 } else {
259 triple_aliases.appendSliceAssumeCapacity(&ARMebTriples);
260 }
261 },
262 .avr => {
263 lib_dirs.appendSliceAssumeCapacity(&AVRLibDirs);
264 triple_aliases.appendSliceAssumeCapacity(&AVRTriples);
265 },
266 .csky => {
267 lib_dirs.appendSliceAssumeCapacity(&CSKYLibDirs);
268 triple_aliases.appendSliceAssumeCapacity(&CSKYTriples);
269 },
270 .x86_64 => {
271 if (target.abi == .gnux32 or target.abi == .muslx32) {
272 lib_dirs.appendSliceAssumeCapacity(&X32LibDirs);
273 triple_aliases.appendSliceAssumeCapacity(&X32Triples);
274 biarch_libdirs.appendSliceAssumeCapacity(&X86_64LibDirs);
275 biarch_triple_aliases.appendSliceAssumeCapacity(&X86_64Triples);
276 } else {
277 lib_dirs.appendSliceAssumeCapacity(&X86_64LibDirs);
278 triple_aliases.appendSliceAssumeCapacity(&X86_64Triples);
279 biarch_libdirs.appendSliceAssumeCapacity(&X32LibDirs);
280 biarch_triple_aliases.appendSliceAssumeCapacity(&X32Triples);
281 }
282 biarch_libdirs.appendSliceAssumeCapacity(&X86LibDirs);
283 biarch_triple_aliases.appendSliceAssumeCapacity(&X86Triples);
284 },
285 .x86 => {
286 lib_dirs.appendSliceAssumeCapacity(&X86LibDirs);
287 // MCU toolchain is 32 bit only and its triple alias is TargetTriple
288 // itself, which will be appended below.
289 if (target.os.tag != .elfiamcu) {
290 triple_aliases.appendSliceAssumeCapacity(&X86Triples);
291 biarch_libdirs.appendSliceAssumeCapacity(&X86_64LibDirs);
292 biarch_triple_aliases.appendSliceAssumeCapacity(&X86_64Triples);
293 biarch_libdirs.appendSliceAssumeCapacity(&X32LibDirs);
294 biarch_triple_aliases.appendSliceAssumeCapacity(&X32Triples);
295 }
296 },
297 .loongarch64 => {
298 lib_dirs.appendSliceAssumeCapacity(&LoongArch64LibDirs);
299 triple_aliases.appendSliceAssumeCapacity(&LoongArch64Triples);
300 },
301 .m68k => {
302 lib_dirs.appendSliceAssumeCapacity(&M68kLibDirs);
303 triple_aliases.appendSliceAssumeCapacity(&M68kTriples);
304 },
305 .mips => {
306 lib_dirs.appendSliceAssumeCapacity(&MIPSLibDirs);
307 triple_aliases.appendSliceAssumeCapacity(&MIPSTriples);
308 biarch_libdirs.appendSliceAssumeCapacity(&MIPS64LibDirs);
309 biarch_triple_aliases.appendSliceAssumeCapacity(&MIPS64Triples);
310 biarch_libdirs.appendSliceAssumeCapacity(&MIPSN32LibDirs);
311 biarch_triple_aliases.appendSliceAssumeCapacity(&MIPSN32Triples);
312 },
313 .mipsel => {
314 lib_dirs.appendSliceAssumeCapacity(&MIPSELLibDirs);
315 triple_aliases.appendSliceAssumeCapacity(&MIPSELTriples);
316 triple_aliases.appendSliceAssumeCapacity(&MIPSTriples);
317 biarch_libdirs.appendSliceAssumeCapacity(&MIPS64ELLibDirs);
318 biarch_triple_aliases.appendSliceAssumeCapacity(&MIPS64ELTriples);
319 biarch_libdirs.appendSliceAssumeCapacity(&MIPSN32ELLibDirs);
320 biarch_triple_aliases.appendSliceAssumeCapacity(&MIPSN32ELTriples);
321 },
322 .mips64 => {
323 lib_dirs.appendSliceAssumeCapacity(&MIPS64LibDirs);
324 triple_aliases.appendSliceAssumeCapacity(&MIPS64Triples);
325 biarch_libdirs.appendSliceAssumeCapacity(&MIPSLibDirs);
326 biarch_triple_aliases.appendSliceAssumeCapacity(&MIPSTriples);
327 biarch_libdirs.appendSliceAssumeCapacity(&MIPSN32LibDirs);
328 biarch_triple_aliases.appendSliceAssumeCapacity(&MIPSN32Triples);
329 },
330 .mips64el => {
331 lib_dirs.appendSliceAssumeCapacity(&MIPS64ELLibDirs);
332 triple_aliases.appendSliceAssumeCapacity(&MIPS64ELTriples);
333 biarch_libdirs.appendSliceAssumeCapacity(&MIPSELLibDirs);
334 biarch_triple_aliases.appendSliceAssumeCapacity(&MIPSELTriples);
335 biarch_libdirs.appendSliceAssumeCapacity(&MIPSN32ELLibDirs);
336 biarch_triple_aliases.appendSliceAssumeCapacity(&MIPSN32ELTriples);
337 biarch_triple_aliases.appendSliceAssumeCapacity(&MIPSTriples);
338 },
339 .msp430 => {
340 lib_dirs.appendSliceAssumeCapacity(&MSP430LibDirs);
341 triple_aliases.appendSliceAssumeCapacity(&MSP430Triples);
342 },
343 .powerpc => {
344 lib_dirs.appendSliceAssumeCapacity(&PPCLibDirs);
345 triple_aliases.appendSliceAssumeCapacity(&PPCTriples);
346 biarch_libdirs.appendSliceAssumeCapacity(&PPC64LibDirs);
347 biarch_triple_aliases.appendSliceAssumeCapacity(&PPC64Triples);
348 },
349 .powerpcle => {
350 lib_dirs.appendSliceAssumeCapacity(&PPCLELibDirs);
351 triple_aliases.appendSliceAssumeCapacity(&PPCLETriples);
352 biarch_libdirs.appendSliceAssumeCapacity(&PPC64LELibDirs);
353 biarch_triple_aliases.appendSliceAssumeCapacity(&PPC64LETriples);
354 },
355 .powerpc64 => {
356 lib_dirs.appendSliceAssumeCapacity(&PPC64LibDirs);
357 triple_aliases.appendSliceAssumeCapacity(&PPC64Triples);
358 biarch_libdirs.appendSliceAssumeCapacity(&PPCLibDirs);
359 biarch_triple_aliases.appendSliceAssumeCapacity(&PPCTriples);
360 },
361 .powerpc64le => {
362 lib_dirs.appendSliceAssumeCapacity(&PPC64LELibDirs);
363 triple_aliases.appendSliceAssumeCapacity(&PPC64LETriples);
364 biarch_libdirs.appendSliceAssumeCapacity(&PPCLELibDirs);
365 biarch_triple_aliases.appendSliceAssumeCapacity(&PPCLETriples);
366 },
367 .riscv32 => {
368 lib_dirs.appendSliceAssumeCapacity(&RISCV32LibDirs);
369 triple_aliases.appendSliceAssumeCapacity(&RISCV32Triples);
370 biarch_libdirs.appendSliceAssumeCapacity(&RISCV64LibDirs);
371 biarch_triple_aliases.appendSliceAssumeCapacity(&RISCV64Triples);
372 },
373 .riscv64 => {
374 lib_dirs.appendSliceAssumeCapacity(&RISCV64LibDirs);
375 triple_aliases.appendSliceAssumeCapacity(&RISCV64Triples);
376 biarch_libdirs.appendSliceAssumeCapacity(&RISCV32LibDirs);
377 biarch_triple_aliases.appendSliceAssumeCapacity(&RISCV32Triples);
378 },
379 .sparc => {
380 lib_dirs.appendSliceAssumeCapacity(&SPARCv8LibDirs);
381 triple_aliases.appendSliceAssumeCapacity(&SPARCv8Triples);
382 biarch_libdirs.appendSliceAssumeCapacity(&SPARCv9LibDirs);
383 biarch_triple_aliases.appendSliceAssumeCapacity(&SPARCv9Triples);
384 },
385 .sparc64 => {
386 lib_dirs.appendSliceAssumeCapacity(&SPARCv9LibDirs);
387 triple_aliases.appendSliceAssumeCapacity(&SPARCv9Triples);
388 biarch_libdirs.appendSliceAssumeCapacity(&SPARCv8LibDirs);
389 biarch_triple_aliases.appendSliceAssumeCapacity(&SPARCv8Triples);
390 },
391 .s390x => {
392 lib_dirs.appendSliceAssumeCapacity(&SystemZLibDirs);
393 triple_aliases.appendSliceAssumeCapacity(&SystemZTriples);
394 },
395 else => {},
396 }
397}
398
399pub fn discover(self: *GCCDetector, tc: *Toolchain) !void {
400 var path_buf: [std.fs.max_path_bytes]u8 = undefined;
401 var fib = std.heap.FixedBufferAllocator.init(&path_buf);
402
403 const target = tc.getTarget();
404 const biarch_variant_target = if (target.ptrBitWidth() == 32)
405 target_util.get64BitArchVariant(target)
406 else
407 target_util.get32BitArchVariant(target);
408
409 var candidate_lib_dirs_buffer: [16][]const u8 = undefined;
410 var candidate_lib_dirs = std.ArrayListUnmanaged([]const u8).initBuffer(&candidate_lib_dirs_buffer);
411
412 var candidate_triple_aliases_buffer: [16][]const u8 = undefined;
413 var candidate_triple_aliases = std.ArrayListUnmanaged([]const u8).initBuffer(&candidate_triple_aliases_buffer);
414
415 var candidate_biarch_lib_dirs_buffer: [16][]const u8 = undefined;
416 var candidate_biarch_lib_dirs = std.ArrayListUnmanaged([]const u8).initBuffer(&candidate_biarch_lib_dirs_buffer);
417
418 var candidate_biarch_triple_aliases_buffer: [16][]const u8 = undefined;
419 var candidate_biarch_triple_aliases = std.ArrayListUnmanaged([]const u8).initBuffer(&candidate_biarch_triple_aliases_buffer);
420
421 try collectLibDirsAndTriples(
422 tc,
423 &candidate_lib_dirs,
424 &candidate_triple_aliases,
425 &candidate_biarch_lib_dirs,
426 &candidate_biarch_triple_aliases,
427 );
428
429 var target_buf: [64]u8 = undefined;
430 const triple_str = target_util.toLLVMTriple(target, &target_buf);
431 candidate_triple_aliases.appendAssumeCapacity(triple_str);
432
433 // Also include the multiarch variant if it's different.
434 var biarch_buf: [64]u8 = undefined;
435 if (biarch_variant_target) |biarch_target| {
436 const biarch_triple_str = target_util.toLLVMTriple(biarch_target, &biarch_buf);
437 if (!std.mem.eql(u8, biarch_triple_str, triple_str)) {
438 candidate_triple_aliases.appendAssumeCapacity(biarch_triple_str);
439 }
440 }
441
442 var prefixes_buf: [16][]const u8 = undefined;
443 var prefixes = std.ArrayListUnmanaged([]const u8).initBuffer(&prefixes_buf);
444 const gcc_toolchain_dir = gccToolchainDir(tc);
445 if (gcc_toolchain_dir.len != 0) {
446 const adjusted = if (gcc_toolchain_dir[gcc_toolchain_dir.len - 1] == '/')
447 gcc_toolchain_dir[0 .. gcc_toolchain_dir.len - 1]
448 else
449 gcc_toolchain_dir;
450 prefixes.appendAssumeCapacity(adjusted);
451 } else {
452 const sysroot = tc.getSysroot();
453 if (sysroot.len > 0) {
454 prefixes.appendAssumeCapacity(sysroot);
455 try addDefaultGCCPrefixes(&prefixes, tc);
456 }
457
458 if (sysroot.len == 0) {
459 try addDefaultGCCPrefixes(&prefixes, tc);
460 }
461 // TODO: Special-case handling for Gentoo
462 }
463
464 const v0 = GCCVersion.parse("0.0.0");
465 for (prefixes.items) |prefix| {
466 if (!tc.filesystem.exists(prefix)) continue;
467
468 for (candidate_lib_dirs.items) |suffix| {
469 defer fib.reset();
470 const lib_dir = std.fs.path.join(fib.allocator(), &.{ prefix, suffix }) catch continue;
471 if (!tc.filesystem.exists(lib_dir)) continue;
472
473 const gcc_dir_exists = tc.filesystem.joinedExists(&.{ lib_dir, "/gcc" });
474 const gcc_cross_dir_exists = tc.filesystem.joinedExists(&.{ lib_dir, "/gcc-cross" });
475
476 try self.scanLibDirForGCCTriple(tc, target, lib_dir, triple_str, false, gcc_dir_exists, gcc_cross_dir_exists);
477 for (candidate_triple_aliases.items) |candidate| {
478 try self.scanLibDirForGCCTriple(tc, target, lib_dir, candidate, false, gcc_dir_exists, gcc_cross_dir_exists);
479 }
480 }
481 for (candidate_biarch_lib_dirs.items) |suffix| {
482 const lib_dir = std.fs.path.join(fib.allocator(), &.{ prefix, suffix }) catch continue;
483 if (!tc.filesystem.exists(lib_dir)) continue;
484
485 const gcc_dir_exists = tc.filesystem.joinedExists(&.{ lib_dir, "/gcc" });
486 const gcc_cross_dir_exists = tc.filesystem.joinedExists(&.{ lib_dir, "/gcc-cross" });
487 for (candidate_biarch_triple_aliases.items) |candidate| {
488 try self.scanLibDirForGCCTriple(tc, target, lib_dir, candidate, true, gcc_dir_exists, gcc_cross_dir_exists);
489 }
490 }
491 if (self.version.order(v0) == .gt) break;
492 }
493}
494
495fn findBiarchMultilibs(
496 tc: *const Toolchain,
497 result: *Multilib.Detected,
498 target: std.Target,
499 path: [2][]const u8,
500 needs_biarch_suffix: bool,
501) !bool {
502 const suff64 = if (target.os.tag == .solaris) switch (target.cpu.arch) {
503 .x86, .x86_64 => "/amd64",
504 .sparc => "/sparcv9",
505 else => "/64",
506 } else "/64";
507
508 const alt_64 = Multilib.init(suff64, suff64, &.{ "-m32", "+m64", "-mx32" });
509 const alt_32 = Multilib.init("/32", "/32", &.{ "+m32", "-m64", "-mx32" });
510 const alt_x32 = Multilib.init("/x32", "/x32", &.{ "-m32", "-m64", "+mx32" });
511
512 const multilib_filter = Multilib.Filter{
513 .base = path,
514 .file = if (target.os.tag == .elfiamcu) "libgcc.a" else "crtbegin.o",
515 };
516
517 const Want = enum {
518 want32,
519 want64,
520 wantx32,
521 };
522 const is_x32 = target.abi == .gnux32 or target.abi == .muslx32;
523 const target_ptr_width = target.ptrBitWidth();
524 const want: Want = if (target_ptr_width == 32 and multilib_filter.exists(alt_32, tc.filesystem))
525 .want64
526 else if (target_ptr_width == 64 and is_x32 and multilib_filter.exists(alt_x32, tc.filesystem))
527 .want64
528 else if (target_ptr_width == 64 and !is_x32 and multilib_filter.exists(alt_64, tc.filesystem))
529 .want32
530 else if (target_ptr_width == 32)
531 if (needs_biarch_suffix) .want64 else .want32
532 else if (is_x32)
533 if (needs_biarch_suffix) .want64 else .wantx32
534 else if (needs_biarch_suffix) .want32 else .want64;
535
536 const default = switch (want) {
537 .want32 => Multilib.init("", "", &.{ "+m32", "-m64", "-mx32" }),
538 .want64 => Multilib.init("", "", &.{ "-m32", "+m64", "-mx32" }),
539 .wantx32 => Multilib.init("", "", &.{ "-m32", "-m64", "+mx32" }),
540 };
541 result.multilibs.appendSliceAssumeCapacity(&.{
542 default,
543 alt_64,
544 alt_32,
545 alt_x32,
546 });
547 result.filter(multilib_filter, tc.filesystem);
548 var flags: Multilib.Flags = .{};
549 flags.appendAssumeCapacity(if (target_ptr_width == 64 and !is_x32) "+m64" else "-m64");
550 flags.appendAssumeCapacity(if (target_ptr_width == 32) "+m32" else "-m32");
551 flags.appendAssumeCapacity(if (target_ptr_width == 64 and is_x32) "+mx32" else "-mx32");
552
553 return result.select(flags);
554}
555
556fn scanGCCForMultilibs(
557 self: *GCCDetector,
558 tc: *const Toolchain,
559 target: std.Target,
560 path: [2][]const u8,
561 needs_biarch_suffix: bool,
562) !bool {
563 var detected: Multilib.Detected = .{};
564 if (target.cpu.arch == .csky) {
565 // TODO
566 } else if (target.cpu.arch.isMIPS()) {
567 // TODO
568 } else if (target.cpu.arch.isRISCV()) {
569 // TODO
570 } else if (target.cpu.arch == .msp430) {
571 // TODO
572 } else if (target.cpu.arch == .avr) {
573 // No multilibs
574 } else if (!try findBiarchMultilibs(tc, &detected, target, path, needs_biarch_suffix)) {
575 return false;
576 }
577 self.selected = detected.selected;
578 self.biarch_sibling = detected.biarch_sibling;
579 return true;
580}
581
582fn scanLibDirForGCCTriple(
583 self: *GCCDetector,
584 tc: *const Toolchain,
585 target: std.Target,
586 lib_dir: []const u8,
587 candidate_triple: []const u8,
588 needs_biarch_suffix: bool,
589 gcc_dir_exists: bool,
590 gcc_cross_dir_exists: bool,
591) !void {
592 var path_buf: [std.fs.max_path_bytes]u8 = undefined;
593 var fib = std.heap.FixedBufferAllocator.init(&path_buf);
594 for (0..2) |i| {
595 if (i == 0 and !gcc_dir_exists) continue;
596 if (i == 1 and !gcc_cross_dir_exists) continue;
597 defer fib.reset();
598
599 const base: []const u8 = if (i == 0) "gcc" else "gcc-cross";
600 var lib_suffix_buf: [64]u8 = undefined;
601 var suffix_buf_fib = std.heap.FixedBufferAllocator.init(&lib_suffix_buf);
602 const lib_suffix = std.fs.path.join(suffix_buf_fib.allocator(), &.{ base, candidate_triple }) catch continue;
603
604 const dir_name = std.fs.path.join(fib.allocator(), &.{ lib_dir, lib_suffix }) catch continue;
605 var parent_dir = tc.filesystem.openDir(dir_name) catch continue;
606 defer parent_dir.close();
607
608 var it = parent_dir.iterate();
609 while (it.next() catch continue) |entry| {
610 if (entry.kind != .directory) continue;
611
612 const version_text = entry.name;
613 const candidate_version = GCCVersion.parse(version_text);
614 if (candidate_version.major != -1) {
615 // TODO: cache path so we're not repeatedly scanning
616 }
617 if (candidate_version.isLessThan(4, 1, 1, "")) continue;
618 switch (candidate_version.order(self.version)) {
619 .lt, .eq => continue,
620 .gt => {},
621 }
622
623 if (!try self.scanGCCForMultilibs(tc, target, .{ dir_name, version_text }, needs_biarch_suffix)) continue;
624
625 self.version = candidate_version;
626 self.gcc_triple = try tc.arena.dupe(u8, candidate_triple);
627 self.install_path = try std.fs.path.join(tc.arena, &.{ lib_dir, lib_suffix, version_text });
628 self.parent_lib_path = try std.fs.path.join(tc.arena, &.{ self.install_path, "..", "..", ".." });
629 self.is_valid = true;
630 }
631 }
632}
633
634fn gccToolchainDir(tc: *const Toolchain) []const u8 {
635 const sysroot = tc.getSysroot();
636 if (sysroot.len != 0) return "";
637 return system_defaults.gcc_install_prefix;
638}
lib/compiler/aro/aro/Driver/GCCVersion.zig deleted-132
...@@ -1,132 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const Order = std.math.Order;
4
5const GCCVersion = @This();
6
7/// Raw version number text
8raw: []const u8 = "",
9
10/// -1 indicates not present
11major: i32 = -1,
12/// -1 indicates not present
13minor: i32 = -1,
14/// -1 indicates not present
15patch: i32 = -1,
16
17/// Text of parsed major version number
18major_str: []const u8 = "",
19/// Text of parsed major + minor version number
20minor_str: []const u8 = "",
21
22/// Patch number suffix
23suffix: []const u8 = "",
24
25/// This orders versions according to the preferred usage order, not a notion of release-time ordering
26/// Higher version numbers are preferred, but nonexistent minor/patch/suffix is preferred to one that does exist
27/// e.g. `4.1` is preferred over `4.0` but `4` is preferred over both `4.0` and `4.1`
28pub fn isLessThan(self: GCCVersion, rhs_major: i32, rhs_minor: i32, rhs_patch: i32, rhs_suffix: []const u8) bool {
29 if (self.major != rhs_major) {
30 return self.major < rhs_major;
31 }
32 if (self.minor != rhs_minor) {
33 if (rhs_minor == -1) return true;
34 if (self.minor == -1) return false;
35 return self.minor < rhs_minor;
36 }
37 if (self.patch != rhs_patch) {
38 if (rhs_patch == -1) return true;
39 if (self.patch == -1) return false;
40 return self.patch < rhs_patch;
41 }
42 if (!mem.eql(u8, self.suffix, rhs_suffix)) {
43 if (rhs_suffix.len == 0) return true;
44 if (self.suffix.len == 0) return false;
45 return switch (std.mem.order(u8, self.suffix, rhs_suffix)) {
46 .lt => true,
47 .eq => unreachable,
48 .gt => false,
49 };
50 }
51 return false;
52}
53
54/// Strings in the returned GCCVersion struct have the same lifetime as `text`
55pub fn parse(text: []const u8) GCCVersion {
56 const bad = GCCVersion{ .major = -1 };
57 var good = bad;
58
59 var it = mem.splitScalar(u8, text, '.');
60 const first = it.next().?;
61 const second = it.next() orelse "";
62 const rest = it.next() orelse "";
63
64 good.major = std.fmt.parseInt(i32, first, 10) catch return bad;
65 if (good.major < 0) return bad;
66 good.major_str = first;
67
68 if (second.len == 0) return good;
69 var minor_str = second;
70
71 if (rest.len == 0) {
72 const end = mem.indexOfNone(u8, minor_str, "0123456789") orelse minor_str.len;
73 if (end > 0) {
74 good.suffix = minor_str[end..];
75 minor_str = minor_str[0..end];
76 }
77 }
78 good.minor = std.fmt.parseInt(i32, minor_str, 10) catch return bad;
79 if (good.minor < 0) return bad;
80 good.minor_str = minor_str;
81
82 if (rest.len > 0) {
83 const end = mem.indexOfNone(u8, rest, "0123456789") orelse rest.len;
84 if (end > 0) {
85 const patch_num_text = rest[0..end];
86 good.patch = std.fmt.parseInt(i32, patch_num_text, 10) catch return bad;
87 if (good.patch < 0) return bad;
88 good.suffix = rest[end..];
89 }
90 }
91
92 return good;
93}
94
95pub fn order(a: GCCVersion, b: GCCVersion) Order {
96 if (a.isLessThan(b.major, b.minor, b.patch, b.suffix)) return .lt;
97 if (b.isLessThan(a.major, a.minor, a.patch, a.suffix)) return .gt;
98 return .eq;
99}
100
101/// Used for determining __GNUC__ macro values
102/// This matches clang's logic for overflowing values
103pub fn toUnsigned(self: GCCVersion) u32 {
104 var result: u32 = 0;
105 if (self.major > 0) result = @as(u32, @intCast(self.major)) *% 10_000;
106 if (self.minor > 0) result +%= @as(u32, @intCast(self.minor)) *% 100;
107 if (self.patch > 0) result +%= @as(u32, @intCast(self.patch));
108 return result;
109}
110
111test parse {
112 const versions = [10]GCCVersion{
113 parse("5"),
114 parse("4"),
115 parse("4.2"),
116 parse("4.0"),
117 parse("4.0-patched"),
118 parse("4.0.2"),
119 parse("4.0.1"),
120 parse("4.0.1-patched"),
121 parse("4.0.0"),
122 parse("4.0.0-patched"),
123 };
124
125 for (versions[0 .. versions.len - 1], versions[1..versions.len]) |first, second| {
126 try std.testing.expectEqual(Order.eq, first.order(first));
127 try std.testing.expectEqual(Order.gt, first.order(second));
128 try std.testing.expectEqual(Order.lt, second.order(first));
129 }
130 const last = versions[versions.len - 1];
131 try std.testing.expectEqual(Order.eq, last.order(last));
132}
lib/compiler/aro/aro/Driver/Multilib.zig deleted-71
...@@ -1,71 +0,0 @@
1const std = @import("std");
2const Filesystem = @import("Filesystem.zig").Filesystem;
3
4pub const Flags = std.BoundedArray([]const u8, 6);
5
6/// Large enough for GCCDetector for Linux; may need to be increased to support other toolchains.
7const max_multilibs = 4;
8
9const MultilibArray = std.BoundedArray(Multilib, max_multilibs);
10
11pub const Detected = struct {
12 multilibs: MultilibArray = .{},
13 selected: Multilib = .{},
14 biarch_sibling: ?Multilib = null,
15
16 pub fn filter(self: *Detected, multilib_filter: Filter, fs: Filesystem) void {
17 var found_count: usize = 0;
18 for (self.multilibs.constSlice()) |multilib| {
19 if (multilib_filter.exists(multilib, fs)) {
20 self.multilibs.set(found_count, multilib);
21 found_count += 1;
22 }
23 }
24 self.multilibs.resize(found_count) catch unreachable;
25 }
26
27 pub fn select(self: *Detected, flags: Flags) !bool {
28 var filtered: MultilibArray = .{};
29 for (self.multilibs.constSlice()) |multilib| {
30 for (multilib.flags.constSlice()) |multilib_flag| {
31 const matched = for (flags.constSlice()) |arg_flag| {
32 if (std.mem.eql(u8, arg_flag[1..], multilib_flag[1..])) break arg_flag;
33 } else multilib_flag;
34 if (matched[0] != multilib_flag[0]) break;
35 } else {
36 filtered.appendAssumeCapacity(multilib);
37 }
38 }
39 if (filtered.len == 0) return false;
40 if (filtered.len == 1) {
41 self.selected = filtered.get(0);
42 return true;
43 }
44 return error.TooManyMultilibs;
45 }
46};
47
48pub const Filter = struct {
49 base: [2][]const u8,
50 file: []const u8,
51 pub fn exists(self: Filter, m: Multilib, fs: Filesystem) bool {
52 return fs.joinedExists(&.{ self.base[0], self.base[1], m.gcc_suffix, self.file });
53 }
54};
55
56const Multilib = @This();
57
58gcc_suffix: []const u8 = "",
59os_suffix: []const u8 = "",
60include_suffix: []const u8 = "",
61flags: Flags = .{},
62priority: u32 = 0,
63
64pub fn init(gcc_suffix: []const u8, os_suffix: []const u8, flags: []const []const u8) Multilib {
65 var self: Multilib = .{
66 .gcc_suffix = gcc_suffix,
67 .os_suffix = os_suffix,
68 };
69 self.flags.appendSliceAssumeCapacity(flags);
70 return self;
71}
lib/compiler/aro/aro/Hideset.zig deleted-196
...@@ -1,196 +0,0 @@
1//! A hideset is a linked list (implemented as an array so that elements are identified by 4-byte indices)
2//! of the set of identifiers from which a token was expanded.
3//! During macro expansion, if a token would otherwise be expanded, but its hideset contains
4//! the token itself, then it is not expanded
5//! Most tokens have an empty hideset, and the hideset is not needed once expansion is complete,
6//! so we use a hash map to store them instead of directly storing them with the token.
7//! The C standard underspecifies the algorithm for updating a token's hideset;
8//! we use the one here: https://www.spinellis.gr/blog/20060626/cpp.algo.pdf
9
10const std = @import("std");
11const mem = std.mem;
12const Allocator = mem.Allocator;
13const Source = @import("Source.zig");
14const Compilation = @import("Compilation.zig");
15const Tokenizer = @import("Tokenizer.zig");
16
17pub const Hideset = @This();
18
19const Identifier = struct {
20 id: Source.Id = .unused,
21 byte_offset: u32 = 0,
22
23 fn slice(self: Identifier, comp: *const Compilation) []const u8 {
24 var tmp_tokenizer = Tokenizer{
25 .buf = comp.getSource(self.id).buf,
26 .langopts = comp.langopts,
27 .index = self.byte_offset,
28 .source = .generated,
29 };
30 const res = tmp_tokenizer.next();
31 return tmp_tokenizer.buf[res.start..res.end];
32 }
33
34 fn fromLocation(loc: Source.Location) Identifier {
35 return .{
36 .id = loc.id,
37 .byte_offset = loc.byte_offset,
38 };
39 }
40};
41
42const Item = struct {
43 identifier: Identifier = .{},
44 next: Index = .none,
45
46 const List = std.MultiArrayList(Item);
47};
48
49pub const Index = enum(u32) {
50 none = std.math.maxInt(u32),
51 _,
52};
53
54map: std.AutoHashMapUnmanaged(Identifier, Index) = .empty,
55/// Used for computing union/intersection of two lists; stored here so that allocations can be retained
56/// until hideset is deinit'ed
57tmp_map: std.AutoHashMapUnmanaged(Identifier, void) = .empty,
58linked_list: Item.List = .{},
59comp: *const Compilation,
60
61/// Invalidated if the underlying MultiArrayList slice is reallocated due to resize
62const Iterator = struct {
63 slice: Item.List.Slice,
64 i: Index,
65
66 fn next(self: *Iterator) ?Identifier {
67 if (self.i == .none) return null;
68 defer self.i = self.slice.items(.next)[@intFromEnum(self.i)];
69 return self.slice.items(.identifier)[@intFromEnum(self.i)];
70 }
71};
72
73pub fn deinit(self: *Hideset) void {
74 self.map.deinit(self.comp.gpa);
75 self.tmp_map.deinit(self.comp.gpa);
76 self.linked_list.deinit(self.comp.gpa);
77}
78
79pub fn clearRetainingCapacity(self: *Hideset) void {
80 self.linked_list.shrinkRetainingCapacity(0);
81 self.map.clearRetainingCapacity();
82}
83
84pub fn clearAndFree(self: *Hideset) void {
85 self.map.clearAndFree(self.comp.gpa);
86 self.tmp_map.clearAndFree(self.comp.gpa);
87 self.linked_list.shrinkAndFree(self.comp.gpa, 0);
88}
89
90/// Iterator is invalidated if the underlying MultiArrayList slice is reallocated due to resize
91fn iterator(self: *const Hideset, idx: Index) Iterator {
92 return Iterator{
93 .slice = self.linked_list.slice(),
94 .i = idx,
95 };
96}
97
98pub fn get(self: *const Hideset, loc: Source.Location) Index {
99 return self.map.get(Identifier.fromLocation(loc)) orelse .none;
100}
101
102pub fn put(self: *Hideset, loc: Source.Location, value: Index) !void {
103 try self.map.put(self.comp.gpa, Identifier.fromLocation(loc), value);
104}
105
106fn ensureUnusedCapacity(self: *Hideset, new_size: usize) !void {
107 try self.linked_list.ensureUnusedCapacity(self.comp.gpa, new_size);
108}
109
110/// Creates a one-item list with contents `identifier`
111fn createNodeAssumeCapacity(self: *Hideset, identifier: Identifier) Index {
112 return self.createNodeAssumeCapacityExtra(identifier, .none);
113}
114
115/// Creates a one-item list with contents `identifier`
116fn createNodeAssumeCapacityExtra(self: *Hideset, identifier: Identifier, next: Index) Index {
117 const next_idx = self.linked_list.len;
118 self.linked_list.appendAssumeCapacity(.{ .identifier = identifier, .next = next });
119 return @enumFromInt(next_idx);
120}
121
122/// Create a new list with `identifier` at the front followed by `tail`
123pub fn prepend(self: *Hideset, loc: Source.Location, tail: Index) !Index {
124 const new_idx = self.linked_list.len;
125 try self.linked_list.append(self.comp.gpa, .{ .identifier = Identifier.fromLocation(loc), .next = tail });
126 return @enumFromInt(new_idx);
127}
128
129/// Attach elements of `b` to the front of `a` (if they're not in `a`)
130pub fn @"union"(self: *Hideset, a: Index, b: Index) !Index {
131 if (a == .none) return b;
132 if (b == .none) return a;
133 self.tmp_map.clearRetainingCapacity();
134
135 var it = self.iterator(b);
136 while (it.next()) |identifier| {
137 try self.tmp_map.put(self.comp.gpa, identifier, {});
138 }
139
140 var head: Index = b;
141 try self.ensureUnusedCapacity(self.len(a));
142 it = self.iterator(a);
143 while (it.next()) |identifier| {
144 if (!self.tmp_map.contains(identifier)) {
145 head = self.createNodeAssumeCapacityExtra(identifier, head);
146 }
147 }
148 return head;
149}
150
151pub fn contains(self: *const Hideset, list: Index, str: []const u8) bool {
152 var it = self.iterator(list);
153 while (it.next()) |identifier| {
154 if (mem.eql(u8, str, identifier.slice(self.comp))) return true;
155 }
156 return false;
157}
158
159fn len(self: *const Hideset, list: Index) usize {
160 const nexts = self.linked_list.items(.next);
161 var cur = list;
162 var count: usize = 0;
163 while (cur != .none) : (count += 1) {
164 cur = nexts[@intFromEnum(cur)];
165 }
166 return count;
167}
168
169pub fn intersection(self: *Hideset, a: Index, b: Index) !Index {
170 if (a == .none or b == .none) return .none;
171 self.tmp_map.clearRetainingCapacity();
172
173 var cur: Index = .none;
174 var head: Index = .none;
175 var it = self.iterator(a);
176 var a_len: usize = 0;
177 while (it.next()) |identifier| : (a_len += 1) {
178 try self.tmp_map.put(self.comp.gpa, identifier, {});
179 }
180 try self.ensureUnusedCapacity(@min(a_len, self.len(b)));
181
182 it = self.iterator(b);
183 while (it.next()) |identifier| {
184 if (self.tmp_map.contains(identifier)) {
185 const new_idx = self.createNodeAssumeCapacity(identifier);
186 if (head == .none) {
187 head = new_idx;
188 }
189 if (cur != .none) {
190 self.linked_list.items(.next)[@intFromEnum(cur)] = new_idx;
191 }
192 cur = new_idx;
193 }
194 }
195 return head;
196}
lib/compiler/aro/aro/InitList.zig deleted-153
...@@ -1,153 +0,0 @@
1//! Sparsely populated list of used indexes.
2//! Used for detecting duplicate initializers.
3const std = @import("std");
4const Allocator = std.mem.Allocator;
5const testing = std.testing;
6const Tree = @import("Tree.zig");
7const Token = Tree.Token;
8const TokenIndex = Tree.TokenIndex;
9const NodeIndex = Tree.NodeIndex;
10const Type = @import("Type.zig");
11const Diagnostics = @import("Diagnostics.zig");
12const NodeList = std.ArrayList(NodeIndex);
13const Parser = @import("Parser.zig");
14
15const Item = struct {
16 list: InitList = .{},
17 index: u64,
18
19 fn order(_: void, a: Item, b: Item) std.math.Order {
20 return std.math.order(a.index, b.index);
21 }
22};
23
24const InitList = @This();
25
26list: std.ArrayListUnmanaged(Item) = .empty,
27node: NodeIndex = .none,
28tok: TokenIndex = 0,
29
30/// Deinitialize freeing all memory.
31pub fn deinit(il: *InitList, gpa: Allocator) void {
32 for (il.list.items) |*item| item.list.deinit(gpa);
33 il.list.deinit(gpa);
34 il.* = undefined;
35}
36
37/// Insert initializer at index, returning previous entry if one exists.
38pub fn put(il: *InitList, gpa: Allocator, index: usize, node: NodeIndex, tok: TokenIndex) !?TokenIndex {
39 const items = il.list.items;
40 var left: usize = 0;
41 var right: usize = items.len;
42
43 // Append new value to empty list
44 if (left == right) {
45 const item = try il.list.addOne(gpa);
46 item.* = .{
47 .list = .{ .node = node, .tok = tok },
48 .index = index,
49 };
50 return null;
51 }
52
53 while (left < right) {
54 // Avoid overflowing in the midpoint calculation
55 const mid = left + (right - left) / 2;
56 // Compare the key with the midpoint element
57 switch (std.math.order(index, items[mid].index)) {
58 .eq => {
59 // Replace previous entry.
60 const prev = items[mid].list.tok;
61 items[mid].list.deinit(gpa);
62 items[mid] = .{
63 .list = .{ .node = node, .tok = tok },
64 .index = index,
65 };
66 return prev;
67 },
68 .gt => left = mid + 1,
69 .lt => right = mid,
70 }
71 }
72
73 // Insert a new value into a sorted position.
74 try il.list.insert(gpa, left, .{
75 .list = .{ .node = node, .tok = tok },
76 .index = index,
77 });
78 return null;
79}
80
81/// Find item at index, create new if one does not exist.
82pub fn find(il: *InitList, gpa: Allocator, index: u64) !*InitList {
83 const items = il.list.items;
84 var left: usize = 0;
85 var right: usize = items.len;
86
87 // Append new value to empty list
88 if (left == right) {
89 const item = try il.list.addOne(gpa);
90 item.* = .{
91 .list = .{ .node = .none, .tok = 0 },
92 .index = index,
93 };
94 return &item.list;
95 }
96
97 while (left < right) {
98 // Avoid overflowing in the midpoint calculation
99 const mid = left + (right - left) / 2;
100 // Compare the key with the midpoint element
101 switch (std.math.order(index, items[mid].index)) {
102 .eq => return &items[mid].list,
103 .gt => left = mid + 1,
104 .lt => right = mid,
105 }
106 }
107
108 // Insert a new value into a sorted position.
109 try il.list.insert(gpa, left, .{
110 .list = .{ .node = .none, .tok = 0 },
111 .index = index,
112 });
113 return &il.list.items[left].list;
114}
115
116test "basic usage" {
117 const gpa = testing.allocator;
118 var il: InitList = .{};
119 defer il.deinit(gpa);
120
121 {
122 var i: usize = 0;
123 while (i < 5) : (i += 1) {
124 const prev = try il.put(gpa, i, .none, 0);
125 try testing.expect(prev == null);
126 }
127 }
128
129 {
130 const failing = testing.failing_allocator;
131 var i: usize = 0;
132 while (i < 5) : (i += 1) {
133 _ = try il.find(failing, i);
134 }
135 }
136
137 {
138 var item = try il.find(gpa, 0);
139 var i: usize = 1;
140 while (i < 5) : (i += 1) {
141 item = try item.find(gpa, i);
142 }
143 }
144
145 {
146 const failing = testing.failing_allocator;
147 var item = try il.find(failing, 0);
148 var i: usize = 1;
149 while (i < 5) : (i += 1) {
150 item = try item.find(failing, i);
151 }
152 }
153}
lib/compiler/aro/aro/LangOpts.zig deleted-176
...@@ -1,176 +0,0 @@
1const std = @import("std");
2const DiagnosticTag = @import("Diagnostics.zig").Tag;
3const char_info = @import("char_info.zig");
4
5pub const Compiler = enum {
6 clang,
7 gcc,
8 msvc,
9};
10
11/// The floating-point evaluation method for intermediate results within a single expression
12pub const FPEvalMethod = enum(i8) {
13 /// The evaluation method cannot be determined or is inconsistent for this target.
14 indeterminate = -1,
15 /// Use the type declared in the source
16 source = 0,
17 /// Use double as the floating-point evaluation method for all float expressions narrower than double.
18 double = 1,
19 /// Use long double as the floating-point evaluation method for all float expressions narrower than long double.
20 extended = 2,
21};
22
23pub const Standard = enum {
24 /// ISO C 1990
25 c89,
26 /// ISO C 1990 with amendment 1
27 iso9899,
28 /// ISO C 1990 with GNU extensions
29 gnu89,
30 /// ISO C 1999
31 c99,
32 /// ISO C 1999 with GNU extensions
33 gnu99,
34 /// ISO C 2011
35 c11,
36 /// ISO C 2011 with GNU extensions
37 gnu11,
38 /// ISO C 2017
39 c17,
40 /// Default value if nothing specified; adds the GNU keywords to
41 /// C17 but does not suppress warnings about using GNU extensions
42 default,
43 /// ISO C 2017 with GNU extensions
44 gnu17,
45 /// Working Draft for ISO C23
46 c23,
47 /// Working Draft for ISO C23 with GNU extensions
48 gnu23,
49
50 const NameMap = std.StaticStringMap(Standard).initComptime(.{
51 .{ "c89", .c89 }, .{ "c90", .c89 }, .{ "iso9899:1990", .c89 },
52 .{ "iso9899:199409", .iso9899 }, .{ "gnu89", .gnu89 }, .{ "gnu90", .gnu89 },
53 .{ "c99", .c99 }, .{ "iso9899:1999", .c99 }, .{ "c9x", .c99 },
54 .{ "iso9899:199x", .c99 }, .{ "gnu99", .gnu99 }, .{ "gnu9x", .gnu99 },
55 .{ "c11", .c11 }, .{ "iso9899:2011", .c11 }, .{ "c1x", .c11 },
56 .{ "iso9899:201x", .c11 }, .{ "gnu11", .gnu11 }, .{ "c17", .c17 },
57 .{ "iso9899:2017", .c17 }, .{ "c18", .c17 }, .{ "iso9899:2018", .c17 },
58 .{ "gnu17", .gnu17 }, .{ "gnu18", .gnu17 }, .{ "c23", .c23 },
59 .{ "gnu23", .gnu23 }, .{ "c2x", .c23 }, .{ "gnu2x", .gnu23 },
60 });
61
62 pub fn atLeast(self: Standard, other: Standard) bool {
63 return @intFromEnum(self) >= @intFromEnum(other);
64 }
65
66 pub fn isGNU(standard: Standard) bool {
67 return switch (standard) {
68 .gnu89, .gnu99, .gnu11, .default, .gnu17, .gnu23 => true,
69 else => false,
70 };
71 }
72
73 pub fn isExplicitGNU(standard: Standard) bool {
74 return standard.isGNU() and standard != .default;
75 }
76
77 /// Value reported by __STDC_VERSION__ macro
78 pub fn StdCVersionMacro(standard: Standard) ?[]const u8 {
79 return switch (standard) {
80 .c89, .gnu89 => null,
81 .iso9899 => "199409L",
82 .c99, .gnu99 => "199901L",
83 .c11, .gnu11 => "201112L",
84 .default, .c17, .gnu17 => "201710L",
85 .c23, .gnu23 => "202311L",
86 };
87 }
88
89 pub fn codepointAllowedInIdentifier(standard: Standard, codepoint: u21, is_start: bool) bool {
90 if (is_start) {
91 return if (standard.atLeast(.c23))
92 char_info.isXidStart(codepoint)
93 else if (standard.atLeast(.c11))
94 char_info.isC11IdChar(codepoint) and !char_info.isC11DisallowedInitialIdChar(codepoint)
95 else
96 char_info.isC99IdChar(codepoint) and !char_info.isC99DisallowedInitialIDChar(codepoint);
97 } else {
98 return if (standard.atLeast(.c23))
99 char_info.isXidContinue(codepoint)
100 else if (standard.atLeast(.c11))
101 char_info.isC11IdChar(codepoint)
102 else
103 char_info.isC99IdChar(codepoint);
104 }
105 }
106};
107
108const LangOpts = @This();
109
110emulate: Compiler = .clang,
111standard: Standard = .default,
112/// -fshort-enums option, makes enums only take up as much space as they need to hold all the values.
113short_enums: bool = false,
114dollars_in_identifiers: bool = true,
115declspec_attrs: bool = false,
116ms_extensions: bool = false,
117/// true or false if digraph support explicitly enabled/disabled with -fdigraphs/-fno-digraphs
118digraphs: ?bool = null,
119/// If set, use the native half type instead of promoting to float
120use_native_half_type: bool = false,
121/// If set, function arguments and return values may be of type __fp16 even if there is no standard ABI for it
122allow_half_args_and_returns: bool = false,
123/// null indicates that the user did not select a value, use target to determine default
124fp_eval_method: ?FPEvalMethod = null,
125/// If set, use specified signedness for `char` instead of the target's default char signedness
126char_signedness_override: ?std.builtin.Signedness = null,
127/// If set, override the default availability of char8_t (by default, enabled in C23 and later; disabled otherwise)
128has_char8_t_override: ?bool = null,
129
130/// Whether to allow GNU-style inline assembly
131gnu_asm: bool = true,
132
133/// Preserve comments when preprocessing
134preserve_comments: bool = false,
135/// Preserve comments in macros when preprocessing
136preserve_comments_in_macros: bool = false,
137
138/// Used ONLY for generating __GNUC__ and related macros. Does not control the presence/absence of any features
139/// Encoded as major * 10,000 + minor * 100 + patch
140/// e.g. 4.2.1 == 40201
141gnuc_version: u32 = 0,
142
143pub fn setStandard(self: *LangOpts, name: []const u8) error{InvalidStandard}!void {
144 self.standard = Standard.NameMap.get(name) orelse return error.InvalidStandard;
145}
146
147pub fn enableMSExtensions(self: *LangOpts) void {
148 self.declspec_attrs = true;
149 self.ms_extensions = true;
150}
151
152pub fn disableMSExtensions(self: *LangOpts) void {
153 self.declspec_attrs = false;
154 self.ms_extensions = true;
155}
156
157pub fn hasChar8_T(self: *const LangOpts) bool {
158 return self.has_char8_t_override orelse self.standard.atLeast(.c23);
159}
160
161pub fn hasDigraphs(self: *const LangOpts) bool {
162 return self.digraphs orelse self.standard.atLeast(.gnu89);
163}
164
165pub fn setEmulatedCompiler(self: *LangOpts, compiler: Compiler) void {
166 self.emulate = compiler;
167 if (compiler == .msvc) self.enableMSExtensions();
168}
169
170pub fn setFpEvalMethod(self: *LangOpts, fp_eval_method: FPEvalMethod) void {
171 self.fp_eval_method = fp_eval_method;
172}
173
174pub fn setCharSignedness(self: *LangOpts, signedness: std.builtin.Signedness) void {
175 self.char_signedness_override = signedness;
176}
lib/compiler/aro/aro/Parser.zig deleted-8891
...@@ -1,8891 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const Allocator = mem.Allocator;
4const assert = std.debug.assert;
5const big = std.math.big;
6const Compilation = @import("Compilation.zig");
7const Source = @import("Source.zig");
8const Tokenizer = @import("Tokenizer.zig");
9const Preprocessor = @import("Preprocessor.zig");
10const Tree = @import("Tree.zig");
11const Token = Tree.Token;
12const NumberPrefix = Token.NumberPrefix;
13const NumberSuffix = Token.NumberSuffix;
14const TokenIndex = Tree.TokenIndex;
15const NodeIndex = Tree.NodeIndex;
16const Type = @import("Type.zig");
17const Diagnostics = @import("Diagnostics.zig");
18const NodeList = std.ArrayList(NodeIndex);
19const InitList = @import("InitList.zig");
20const Attribute = @import("Attribute.zig");
21const char_info = @import("char_info.zig");
22const text_literal = @import("text_literal.zig");
23const Value = @import("Value.zig");
24const SymbolStack = @import("SymbolStack.zig");
25const Symbol = SymbolStack.Symbol;
26const record_layout = @import("record_layout.zig");
27const StrInt = @import("StringInterner.zig");
28const StringId = StrInt.StringId;
29const Builtins = @import("Builtins.zig");
30const Builtin = Builtins.Builtin;
31const evalBuiltin = @import("Builtins/eval.zig").eval;
32const target_util = @import("target.zig");
33
34const Switch = struct {
35 default: ?TokenIndex = null,
36 ranges: std.ArrayList(Range),
37 ty: Type,
38 comp: *Compilation,
39
40 const Range = struct {
41 first: Value,
42 last: Value,
43 tok: TokenIndex,
44 };
45
46 fn add(self: *Switch, first: Value, last: Value, tok: TokenIndex) !?Range {
47 for (self.ranges.items) |range| {
48 if (last.compare(.gte, range.first, self.comp) and first.compare(.lte, range.last, self.comp)) {
49 return range; // They overlap.
50 }
51 }
52 try self.ranges.append(.{
53 .first = first,
54 .last = last,
55 .tok = tok,
56 });
57 return null;
58 }
59};
60
61const Label = union(enum) {
62 unresolved_goto: TokenIndex,
63 label: TokenIndex,
64};
65
66pub const Error = Compilation.Error || error{ParsingFailed};
67
68/// An attribute that has been parsed but not yet validated in its context
69const TentativeAttribute = struct {
70 attr: Attribute,
71 tok: TokenIndex,
72};
73
74/// How the parser handles const int decl references when it is expecting an integer
75/// constant expression.
76const ConstDeclFoldingMode = enum {
77 /// fold const decls as if they were literals
78 fold_const_decls,
79 /// fold const decls as if they were literals and issue GNU extension diagnostic
80 gnu_folding_extension,
81 /// fold const decls as if they were literals and issue VLA diagnostic
82 gnu_vla_folding_extension,
83 /// folding const decls is prohibited; return an unavailable value
84 no_const_decl_folding,
85};
86
87const Parser = @This();
88
89// values from preprocessor
90pp: *Preprocessor,
91comp: *Compilation,
92gpa: mem.Allocator,
93tok_ids: []const Token.Id,
94tok_i: TokenIndex = 0,
95
96// values of the incomplete Tree
97arena: Allocator,
98nodes: Tree.Node.List = .{},
99data: NodeList,
100value_map: Tree.ValueMap,
101
102// buffers used during compilation
103syms: SymbolStack = .{},
104strings: std.ArrayListAligned(u8, 4),
105labels: std.ArrayList(Label),
106list_buf: NodeList,
107decl_buf: NodeList,
108param_buf: std.ArrayList(Type.Func.Param),
109enum_buf: std.ArrayList(Type.Enum.Field),
110record_buf: std.ArrayList(Type.Record.Field),
111attr_buf: std.MultiArrayList(TentativeAttribute) = .{},
112attr_application_buf: std.ArrayListUnmanaged(Attribute) = .empty,
113field_attr_buf: std.ArrayList([]const Attribute),
114/// type name -> variable name location for tentative definitions (top-level defs with thus-far-incomplete types)
115/// e.g. `struct Foo bar;` where `struct Foo` is not defined yet.
116/// The key is the StringId of `Foo` and the value is the TokenIndex of `bar`
117/// Items are removed if the type is subsequently completed with a definition.
118/// We only store the first tentative definition that uses a given type because this map is only used
119/// for issuing an error message, and correcting the first error for a type will fix all of them for that type.
120tentative_defs: std.AutoHashMapUnmanaged(StringId, TokenIndex) = .empty,
121
122// configuration and miscellaneous info
123no_eval: bool = false,
124in_macro: bool = false,
125extension_suppressed: bool = false,
126contains_address_of_label: bool = false,
127label_count: u32 = 0,
128const_decl_folding: ConstDeclFoldingMode = .fold_const_decls,
129/// location of first computed goto in function currently being parsed
130/// if a computed goto is used, the function must contain an
131/// address-of-label expression (tracked with contains_address_of_label)
132computed_goto_tok: ?TokenIndex = null,
133
134/// __auto_type may only be used with a single declarator. Keep track of the name
135/// so that it is not used in its own initializer.
136auto_type_decl_name: StringId = .empty,
137
138/// Various variables that are different for each function.
139func: struct {
140 /// null if not in function, will always be plain func, var_args_func or old_style_func
141 ty: ?Type = null,
142 name: TokenIndex = 0,
143 ident: ?Result = null,
144 pretty_ident: ?Result = null,
145} = .{},
146/// Various variables that are different for each record.
147record: struct {
148 // invalid means we're not parsing a record
149 kind: Token.Id = .invalid,
150 flexible_field: ?TokenIndex = null,
151 start: usize = 0,
152 field_attr_start: usize = 0,
153
154 fn addField(r: @This(), p: *Parser, name: StringId, tok: TokenIndex) Error!void {
155 var i = p.record_members.items.len;
156 while (i > r.start) {
157 i -= 1;
158 if (p.record_members.items[i].name == name) {
159 try p.errStr(.duplicate_member, tok, p.tokSlice(tok));
160 try p.errTok(.previous_definition, p.record_members.items[i].tok);
161 break;
162 }
163 }
164 try p.record_members.append(p.gpa, .{ .name = name, .tok = tok });
165 }
166
167 fn addFieldsFromAnonymous(r: @This(), p: *Parser, ty: Type) Error!void {
168 for (ty.getRecord().?.fields) |f| {
169 if (f.isAnonymousRecord()) {
170 try r.addFieldsFromAnonymous(p, f.ty.canonicalize(.standard));
171 } else if (f.name_tok != 0) {
172 try r.addField(p, f.name, f.name_tok);
173 }
174 }
175 }
176} = .{},
177record_members: std.ArrayListUnmanaged(struct { tok: TokenIndex, name: StringId }) = .empty,
178@"switch": ?*Switch = null,
179in_loop: bool = false,
180pragma_pack: ?u8 = null,
181string_ids: struct {
182 declspec_id: StringId,
183 main_id: StringId,
184 file: StringId,
185 jmp_buf: StringId,
186 sigjmp_buf: StringId,
187 ucontext_t: StringId,
188},
189
190/// Checks codepoint for various pedantic warnings
191/// Returns true if diagnostic issued
192fn checkIdentifierCodepointWarnings(comp: *Compilation, codepoint: u21, loc: Source.Location) Compilation.Error!bool {
193 assert(codepoint >= 0x80);
194
195 const err_start = comp.diagnostics.list.items.len;
196
197 if (!char_info.isC99IdChar(codepoint)) {
198 try comp.addDiagnostic(.{
199 .tag = .c99_compat,
200 .loc = loc,
201 }, &.{});
202 }
203 if (char_info.isInvisible(codepoint)) {
204 try comp.addDiagnostic(.{
205 .tag = .unicode_zero_width,
206 .loc = loc,
207 .extra = .{ .actual_codepoint = codepoint },
208 }, &.{});
209 }
210 if (char_info.homoglyph(codepoint)) |resembles| {
211 try comp.addDiagnostic(.{
212 .tag = .unicode_homoglyph,
213 .loc = loc,
214 .extra = .{ .codepoints = .{ .actual = codepoint, .resembles = resembles } },
215 }, &.{});
216 }
217 return comp.diagnostics.list.items.len != err_start;
218}
219
220/// Issues diagnostics for the current extended identifier token
221/// Return value indicates whether the token should be considered an identifier
222/// true means consider the token to actually be an identifier
223/// false means it is not
224fn validateExtendedIdentifier(p: *Parser) !bool {
225 assert(p.tok_ids[p.tok_i] == .extended_identifier);
226
227 const slice = p.tokSlice(p.tok_i);
228 const view = std.unicode.Utf8View.init(slice) catch {
229 try p.errTok(.invalid_utf8, p.tok_i);
230 return error.FatalError;
231 };
232 var it = view.iterator();
233
234 var valid_identifier = true;
235 var warned = false;
236 var len: usize = 0;
237 var invalid_char: u21 = undefined;
238 var loc = p.pp.tokens.items(.loc)[p.tok_i];
239
240 var normalized = true;
241 var last_canonical_class: char_info.CanonicalCombiningClass = .not_reordered;
242 const standard = p.comp.langopts.standard;
243 while (it.nextCodepoint()) |codepoint| {
244 defer {
245 len += 1;
246 loc.byte_offset += std.unicode.utf8CodepointSequenceLength(codepoint) catch unreachable;
247 }
248 if (codepoint == '$') {
249 warned = true;
250 if (p.comp.langopts.dollars_in_identifiers) try p.comp.addDiagnostic(.{
251 .tag = .dollar_in_identifier_extension,
252 .loc = loc,
253 }, &.{});
254 }
255
256 if (codepoint <= 0x7F) continue;
257 if (!valid_identifier) continue;
258
259 const allowed = standard.codepointAllowedInIdentifier(codepoint, len == 0);
260 if (!allowed) {
261 invalid_char = codepoint;
262 valid_identifier = false;
263 continue;
264 }
265
266 if (!warned) {
267 warned = try checkIdentifierCodepointWarnings(p.comp, codepoint, loc);
268 }
269
270 // Check NFC normalization.
271 if (!normalized) continue;
272 const canonical_class = char_info.getCanonicalClass(codepoint);
273 if (@intFromEnum(last_canonical_class) > @intFromEnum(canonical_class) and
274 canonical_class != .not_reordered)
275 {
276 normalized = false;
277 try p.errStr(.identifier_not_normalized, p.tok_i, slice);
278 continue;
279 }
280 if (char_info.isNormalized(codepoint) != .yes) {
281 normalized = false;
282 try p.errExtra(.identifier_not_normalized, p.tok_i, .{ .normalized = slice });
283 }
284 last_canonical_class = canonical_class;
285 }
286
287 if (!valid_identifier) {
288 if (len == 1) {
289 try p.errExtra(.unexpected_character, p.tok_i, .{ .actual_codepoint = invalid_char });
290 return false;
291 } else {
292 try p.errExtra(.invalid_identifier_start_char, p.tok_i, .{ .actual_codepoint = invalid_char });
293 }
294 }
295
296 return true;
297}
298
299fn eatIdentifier(p: *Parser) !?TokenIndex {
300 switch (p.tok_ids[p.tok_i]) {
301 .identifier => {},
302 .extended_identifier => {
303 if (!try p.validateExtendedIdentifier()) {
304 p.tok_i += 1;
305 return null;
306 }
307 },
308 else => return null,
309 }
310 p.tok_i += 1;
311
312 // Handle illegal '$' characters in identifiers
313 if (!p.comp.langopts.dollars_in_identifiers) {
314 if (p.tok_ids[p.tok_i] == .invalid and p.tokSlice(p.tok_i)[0] == '$') {
315 try p.err(.dollars_in_identifiers);
316 p.tok_i += 1;
317 return error.ParsingFailed;
318 }
319 }
320
321 return p.tok_i - 1;
322}
323
324fn expectIdentifier(p: *Parser) Error!TokenIndex {
325 const actual = p.tok_ids[p.tok_i];
326 if (actual != .identifier and actual != .extended_identifier) {
327 return p.errExpectedToken(.identifier, actual);
328 }
329
330 return (try p.eatIdentifier()) orelse error.ParsingFailed;
331}
332
333fn eatToken(p: *Parser, id: Token.Id) ?TokenIndex {
334 assert(id != .identifier and id != .extended_identifier); // use eatIdentifier
335 if (p.tok_ids[p.tok_i] == id) {
336 defer p.tok_i += 1;
337 return p.tok_i;
338 } else return null;
339}
340
341fn expectToken(p: *Parser, expected: Token.Id) Error!TokenIndex {
342 assert(expected != .identifier and expected != .extended_identifier); // use expectIdentifier
343 const actual = p.tok_ids[p.tok_i];
344 if (actual != expected) return p.errExpectedToken(expected, actual);
345 defer p.tok_i += 1;
346 return p.tok_i;
347}
348
349pub fn tokSlice(p: *Parser, tok: TokenIndex) []const u8 {
350 if (p.tok_ids[tok].lexeme()) |some| return some;
351 const loc = p.pp.tokens.items(.loc)[tok];
352 var tmp_tokenizer = Tokenizer{
353 .buf = p.comp.getSource(loc.id).buf,
354 .langopts = p.comp.langopts,
355 .index = loc.byte_offset,
356 .source = .generated,
357 };
358 const res = tmp_tokenizer.next();
359 return tmp_tokenizer.buf[res.start..res.end];
360}
361
362fn expectClosing(p: *Parser, opening: TokenIndex, id: Token.Id) Error!void {
363 _ = p.expectToken(id) catch |e| {
364 if (e == error.ParsingFailed) {
365 try p.errTok(switch (id) {
366 .r_paren => .to_match_paren,
367 .r_brace => .to_match_brace,
368 .r_bracket => .to_match_brace,
369 else => unreachable,
370 }, opening);
371 }
372 return e;
373 };
374}
375
376fn errOverflow(p: *Parser, op_tok: TokenIndex, res: Result) !void {
377 try p.errStr(.overflow, op_tok, try res.str(p));
378}
379
380fn errExpectedToken(p: *Parser, expected: Token.Id, actual: Token.Id) Error {
381 switch (actual) {
382 .invalid => try p.errExtra(.expected_invalid, p.tok_i, .{ .tok_id_expected = expected }),
383 .eof => try p.errExtra(.expected_eof, p.tok_i, .{ .tok_id_expected = expected }),
384 else => try p.errExtra(.expected_token, p.tok_i, .{ .tok_id = .{
385 .expected = expected,
386 .actual = actual,
387 } }),
388 }
389 return error.ParsingFailed;
390}
391
392pub fn errStr(p: *Parser, tag: Diagnostics.Tag, tok_i: TokenIndex, str: []const u8) Compilation.Error!void {
393 @branchHint(.cold);
394 return p.errExtra(tag, tok_i, .{ .str = str });
395}
396
397pub fn errExtra(p: *Parser, tag: Diagnostics.Tag, tok_i: TokenIndex, extra: Diagnostics.Message.Extra) Compilation.Error!void {
398 @branchHint(.cold);
399 const tok = p.pp.tokens.get(tok_i);
400 var loc = tok.loc;
401 if (tok_i != 0 and tok.id == .eof) {
402 // if the token is EOF, point at the end of the previous token instead
403 const prev = p.pp.tokens.get(tok_i - 1);
404 loc = prev.loc;
405 loc.byte_offset += @intCast(p.tokSlice(tok_i - 1).len);
406 }
407 try p.comp.addDiagnostic(.{
408 .tag = tag,
409 .loc = loc,
410 .extra = extra,
411 }, p.pp.expansionSlice(tok_i));
412}
413
414pub fn errTok(p: *Parser, tag: Diagnostics.Tag, tok_i: TokenIndex) Compilation.Error!void {
415 @branchHint(.cold);
416 return p.errExtra(tag, tok_i, .{ .none = {} });
417}
418
419pub fn err(p: *Parser, tag: Diagnostics.Tag) Compilation.Error!void {
420 @branchHint(.cold);
421 return p.errExtra(tag, p.tok_i, .{ .none = {} });
422}
423
424pub fn todo(p: *Parser, msg: []const u8) Error {
425 try p.errStr(.todo, p.tok_i, msg);
426 return error.ParsingFailed;
427}
428
429pub fn removeNull(p: *Parser, str: Value) !Value {
430 const strings_top = p.strings.items.len;
431 defer p.strings.items.len = strings_top;
432 {
433 const bytes = p.comp.interner.get(str.ref()).bytes;
434 try p.strings.appendSlice(bytes[0 .. bytes.len - 1]);
435 }
436 return Value.intern(p.comp, .{ .bytes = p.strings.items[strings_top..] });
437}
438
439pub fn typeStr(p: *Parser, ty: Type) ![]const u8 {
440 if (@import("builtin").mode != .Debug) {
441 if (ty.is(.invalid)) {
442 return "Tried to render invalid type - this is an aro bug.";
443 }
444 }
445 if (Type.Builder.fromType(ty).str(p.comp.langopts)) |str| return str;
446 const strings_top = p.strings.items.len;
447 defer p.strings.items.len = strings_top;
448
449 const mapper = p.comp.string_interner.getSlowTypeMapper();
450 try ty.print(mapper, p.comp.langopts, p.strings.writer());
451 return try p.comp.diagnostics.arena.allocator().dupe(u8, p.strings.items[strings_top..]);
452}
453
454pub fn typePairStr(p: *Parser, a: Type, b: Type) ![]const u8 {
455 return p.typePairStrExtra(a, " and ", b);
456}
457
458pub fn typePairStrExtra(p: *Parser, a: Type, msg: []const u8, b: Type) ![]const u8 {
459 if (@import("builtin").mode != .Debug) {
460 if (a.is(.invalid) or b.is(.invalid)) {
461 return "Tried to render invalid type - this is an aro bug.";
462 }
463 }
464 const strings_top = p.strings.items.len;
465 defer p.strings.items.len = strings_top;
466
467 try p.strings.append('\'');
468 const mapper = p.comp.string_interner.getSlowTypeMapper();
469 try a.print(mapper, p.comp.langopts, p.strings.writer());
470 try p.strings.append('\'');
471 try p.strings.appendSlice(msg);
472 try p.strings.append('\'');
473 try b.print(mapper, p.comp.langopts, p.strings.writer());
474 try p.strings.append('\'');
475 return try p.comp.diagnostics.arena.allocator().dupe(u8, p.strings.items[strings_top..]);
476}
477
478pub fn valueChangedStr(p: *Parser, res: *Result, old_value: Value, int_ty: Type) ![]const u8 {
479 const strings_top = p.strings.items.len;
480 defer p.strings.items.len = strings_top;
481
482 var w = p.strings.writer();
483 const type_pair_str = try p.typePairStrExtra(res.ty, " to ", int_ty);
484 try w.writeAll(type_pair_str);
485
486 try w.writeAll(" changes ");
487 if (res.val.isZero(p.comp)) try w.writeAll("non-zero ");
488 try w.writeAll("value from ");
489 try old_value.print(res.ty, p.comp, w);
490 try w.writeAll(" to ");
491 try res.val.print(int_ty, p.comp, w);
492
493 return try p.comp.diagnostics.arena.allocator().dupe(u8, p.strings.items[strings_top..]);
494}
495
496fn checkDeprecatedUnavailable(p: *Parser, ty: Type, usage_tok: TokenIndex, decl_tok: TokenIndex) !void {
497 if (ty.getAttribute(.@"error")) |@"error"| {
498 const strings_top = p.strings.items.len;
499 defer p.strings.items.len = strings_top;
500
501 const w = p.strings.writer();
502 const msg_str = p.comp.interner.get(@"error".msg.ref()).bytes;
503 try w.print("call to '{s}' declared with attribute error: {}", .{
504 p.tokSlice(@"error".__name_tok), std.zig.fmtEscapes(msg_str),
505 });
506 const str = try p.comp.diagnostics.arena.allocator().dupe(u8, p.strings.items[strings_top..]);
507 try p.errStr(.error_attribute, usage_tok, str);
508 }
509 if (ty.getAttribute(.warning)) |warning| {
510 const strings_top = p.strings.items.len;
511 defer p.strings.items.len = strings_top;
512
513 const w = p.strings.writer();
514 const msg_str = p.comp.interner.get(warning.msg.ref()).bytes;
515 try w.print("call to '{s}' declared with attribute warning: {}", .{
516 p.tokSlice(warning.__name_tok), std.zig.fmtEscapes(msg_str),
517 });
518 const str = try p.comp.diagnostics.arena.allocator().dupe(u8, p.strings.items[strings_top..]);
519 try p.errStr(.warning_attribute, usage_tok, str);
520 }
521 if (ty.getAttribute(.unavailable)) |unavailable| {
522 try p.errDeprecated(.unavailable, usage_tok, unavailable.msg);
523 try p.errStr(.unavailable_note, unavailable.__name_tok, p.tokSlice(decl_tok));
524 return error.ParsingFailed;
525 } else if (ty.getAttribute(.deprecated)) |deprecated| {
526 try p.errDeprecated(.deprecated_declarations, usage_tok, deprecated.msg);
527 try p.errStr(.deprecated_note, deprecated.__name_tok, p.tokSlice(decl_tok));
528 }
529}
530
531fn errDeprecated(p: *Parser, tag: Diagnostics.Tag, tok_i: TokenIndex, msg: ?Value) Compilation.Error!void {
532 const strings_top = p.strings.items.len;
533 defer p.strings.items.len = strings_top;
534
535 const w = p.strings.writer();
536 try w.print("'{s}' is ", .{p.tokSlice(tok_i)});
537 const reason: []const u8 = switch (tag) {
538 .unavailable => "unavailable",
539 .deprecated_declarations => "deprecated",
540 else => unreachable,
541 };
542 try w.writeAll(reason);
543 if (msg) |m| {
544 const str = p.comp.interner.get(m.ref()).bytes;
545 try w.print(": {}", .{std.zig.fmtEscapes(str)});
546 }
547 const str = try p.comp.diagnostics.arena.allocator().dupe(u8, p.strings.items[strings_top..]);
548 return p.errStr(tag, tok_i, str);
549}
550
551fn addNode(p: *Parser, node: Tree.Node) Allocator.Error!NodeIndex {
552 if (p.in_macro) return .none;
553 const res = p.nodes.len;
554 try p.nodes.append(p.gpa, node);
555 return @enumFromInt(res);
556}
557
558fn addList(p: *Parser, nodes: []const NodeIndex) Allocator.Error!Tree.Node.Range {
559 if (p.in_macro) return Tree.Node.Range{ .start = 0, .end = 0 };
560 const start: u32 = @intCast(p.data.items.len);
561 try p.data.appendSlice(nodes);
562 const end: u32 = @intCast(p.data.items.len);
563 return Tree.Node.Range{ .start = start, .end = end };
564}
565
566fn findLabel(p: *Parser, name: []const u8) ?TokenIndex {
567 for (p.labels.items) |item| {
568 switch (item) {
569 .label => |l| if (mem.eql(u8, p.tokSlice(l), name)) return l,
570 .unresolved_goto => {},
571 }
572 }
573 return null;
574}
575
576fn nodeIs(p: *Parser, node: NodeIndex, tag: Tree.Tag) bool {
577 return p.getNode(node, tag) != null;
578}
579
580pub fn getDecayedStringLiteral(p: *Parser, node: NodeIndex) ?Value {
581 const cast_node = p.getNode(node, .implicit_cast) orelse return null;
582 const data = p.nodes.items(.data)[@intFromEnum(cast_node)];
583 if (data.cast.kind != .array_to_pointer) return null;
584 const literal_node = p.getNode(data.cast.operand, .string_literal_expr) orelse return null;
585 return p.value_map.get(literal_node);
586}
587
588fn getNode(p: *Parser, node: NodeIndex, tag: Tree.Tag) ?NodeIndex {
589 var cur = node;
590 const tags = p.nodes.items(.tag);
591 const data = p.nodes.items(.data);
592 while (true) {
593 const cur_tag = tags[@intFromEnum(cur)];
594 if (cur_tag == .paren_expr) {
595 cur = data[@intFromEnum(cur)].un;
596 } else if (cur_tag == tag) {
597 return cur;
598 } else {
599 return null;
600 }
601 }
602}
603
604fn nodeIsCompoundLiteral(p: *Parser, node: NodeIndex) bool {
605 var cur = node;
606 const tags = p.nodes.items(.tag);
607 const data = p.nodes.items(.data);
608 while (true) {
609 switch (tags[@intFromEnum(cur)]) {
610 .paren_expr => cur = data[@intFromEnum(cur)].un,
611 .compound_literal_expr,
612 .static_compound_literal_expr,
613 .thread_local_compound_literal_expr,
614 .static_thread_local_compound_literal_expr,
615 => return true,
616 else => return false,
617 }
618 }
619}
620
621fn tmpTree(p: *Parser) Tree {
622 return .{
623 .nodes = p.nodes.slice(),
624 .data = p.data.items,
625 .value_map = p.value_map,
626 .comp = p.comp,
627 .arena = undefined,
628 .generated = undefined,
629 .tokens = undefined,
630 .root_decls = undefined,
631 };
632}
633
634fn pragma(p: *Parser) Compilation.Error!bool {
635 var found_pragma = false;
636 while (p.eatToken(.keyword_pragma)) |_| {
637 found_pragma = true;
638
639 const name_tok = p.tok_i;
640 const name = p.tokSlice(name_tok);
641
642 const end_idx = mem.indexOfScalarPos(Token.Id, p.tok_ids, p.tok_i, .nl).?;
643 const pragma_len = @as(TokenIndex, @intCast(end_idx)) - p.tok_i;
644 defer p.tok_i += pragma_len + 1; // skip past .nl as well
645 if (p.comp.getPragma(name)) |prag| {
646 try prag.parserCB(p, p.tok_i);
647 }
648 }
649 return found_pragma;
650}
651
652/// Issue errors for top-level definitions whose type was never completed.
653fn diagnoseIncompleteDefinitions(p: *Parser) !void {
654 @branchHint(.cold);
655
656 const node_slices = p.nodes.slice();
657 const tags = node_slices.items(.tag);
658 const tys = node_slices.items(.ty);
659 const data = node_slices.items(.data);
660
661 for (p.decl_buf.items) |decl_node| {
662 const idx = @intFromEnum(decl_node);
663 switch (tags[idx]) {
664 .struct_forward_decl, .union_forward_decl, .enum_forward_decl => {},
665 else => continue,
666 }
667
668 const ty = tys[idx];
669 const decl_type_name = if (ty.getRecord()) |rec|
670 rec.name
671 else if (ty.get(.@"enum")) |en|
672 en.data.@"enum".name
673 else
674 unreachable;
675
676 const tentative_def_tok = p.tentative_defs.get(decl_type_name) orelse continue;
677 const type_str = try p.typeStr(ty);
678 try p.errStr(.tentative_definition_incomplete, tentative_def_tok, type_str);
679 try p.errStr(.forward_declaration_here, data[idx].decl_ref, type_str);
680 }
681}
682
683/// root : (decl | assembly ';' | staticAssert)*
684pub fn parse(pp: *Preprocessor) Compilation.Error!Tree {
685 assert(pp.linemarkers == .none);
686 pp.comp.pragmaEvent(.before_parse);
687
688 var arena = std.heap.ArenaAllocator.init(pp.comp.gpa);
689 errdefer arena.deinit();
690 var p = Parser{
691 .pp = pp,
692 .comp = pp.comp,
693 .gpa = pp.comp.gpa,
694 .arena = arena.allocator(),
695 .tok_ids = pp.tokens.items(.id),
696 .strings = std.ArrayListAligned(u8, 4).init(pp.comp.gpa),
697 .value_map = Tree.ValueMap.init(pp.comp.gpa),
698 .data = NodeList.init(pp.comp.gpa),
699 .labels = std.ArrayList(Label).init(pp.comp.gpa),
700 .list_buf = NodeList.init(pp.comp.gpa),
701 .decl_buf = NodeList.init(pp.comp.gpa),
702 .param_buf = std.ArrayList(Type.Func.Param).init(pp.comp.gpa),
703 .enum_buf = std.ArrayList(Type.Enum.Field).init(pp.comp.gpa),
704 .record_buf = std.ArrayList(Type.Record.Field).init(pp.comp.gpa),
705 .field_attr_buf = std.ArrayList([]const Attribute).init(pp.comp.gpa),
706 .string_ids = .{
707 .declspec_id = try StrInt.intern(pp.comp, "__declspec"),
708 .main_id = try StrInt.intern(pp.comp, "main"),
709 .file = try StrInt.intern(pp.comp, "FILE"),
710 .jmp_buf = try StrInt.intern(pp.comp, "jmp_buf"),
711 .sigjmp_buf = try StrInt.intern(pp.comp, "sigjmp_buf"),
712 .ucontext_t = try StrInt.intern(pp.comp, "ucontext_t"),
713 },
714 };
715 errdefer {
716 p.nodes.deinit(pp.comp.gpa);
717 p.value_map.deinit();
718 }
719 defer {
720 p.data.deinit();
721 p.labels.deinit();
722 p.strings.deinit();
723 p.syms.deinit(pp.comp.gpa);
724 p.list_buf.deinit();
725 p.decl_buf.deinit();
726 p.param_buf.deinit();
727 p.enum_buf.deinit();
728 p.record_buf.deinit();
729 p.record_members.deinit(pp.comp.gpa);
730 p.attr_buf.deinit(pp.comp.gpa);
731 p.attr_application_buf.deinit(pp.comp.gpa);
732 p.tentative_defs.deinit(pp.comp.gpa);
733 assert(p.field_attr_buf.items.len == 0);
734 p.field_attr_buf.deinit();
735 }
736
737 try p.syms.pushScope(&p);
738 defer p.syms.popScope();
739
740 // NodeIndex 0 must be invalid
741 _ = try p.addNode(.{ .tag = .invalid, .ty = undefined, .data = undefined, .loc = undefined });
742
743 {
744 if (p.comp.langopts.hasChar8_T()) {
745 try p.syms.defineTypedef(&p, try StrInt.intern(p.comp, "char8_t"), .{ .specifier = .uchar }, 0, .none);
746 }
747 try p.syms.defineTypedef(&p, try StrInt.intern(p.comp, "__int128_t"), .{ .specifier = .int128 }, 0, .none);
748 try p.syms.defineTypedef(&p, try StrInt.intern(p.comp, "__uint128_t"), .{ .specifier = .uint128 }, 0, .none);
749
750 const elem_ty = try p.arena.create(Type);
751 elem_ty.* = .{ .specifier = .char };
752 try p.syms.defineTypedef(&p, try StrInt.intern(p.comp, "__builtin_ms_va_list"), .{
753 .specifier = .pointer,
754 .data = .{ .sub_type = elem_ty },
755 }, 0, .none);
756
757 const ty = &pp.comp.types.va_list;
758 try p.syms.defineTypedef(&p, try StrInt.intern(p.comp, "__builtin_va_list"), ty.*, 0, .none);
759
760 if (ty.isArray()) ty.decayArray();
761
762 try p.syms.defineTypedef(&p, try StrInt.intern(p.comp, "__NSConstantString"), pp.comp.types.ns_constant_string.ty, 0, .none);
763
764 if (p.comp.float80Type()) |float80_ty| {
765 try p.syms.defineTypedef(&p, try StrInt.intern(p.comp, "__float80"), float80_ty, 0, .none);
766 }
767 }
768
769 while (p.eatToken(.eof) == null) {
770 if (try p.pragma()) continue;
771 if (try p.parseOrNextDecl(staticAssert)) continue;
772 if (try p.parseOrNextDecl(decl)) continue;
773 if (p.eatToken(.keyword_extension)) |_| {
774 const saved_extension = p.extension_suppressed;
775 defer p.extension_suppressed = saved_extension;
776 p.extension_suppressed = true;
777
778 if (try p.parseOrNextDecl(decl)) continue;
779 switch (p.tok_ids[p.tok_i]) {
780 .semicolon => p.tok_i += 1,
781 .keyword_static_assert,
782 .keyword_c23_static_assert,
783 .keyword_pragma,
784 .keyword_extension,
785 .keyword_asm,
786 .keyword_asm1,
787 .keyword_asm2,
788 => {},
789 else => try p.err(.expected_external_decl),
790 }
791 continue;
792 }
793 if (p.assembly(.global) catch |er| switch (er) {
794 error.ParsingFailed => {
795 p.nextExternDecl();
796 continue;
797 },
798 else => |e| return e,
799 }) |node| {
800 try p.decl_buf.append(node);
801 continue;
802 }
803 if (p.eatToken(.semicolon)) |tok| {
804 try p.errTok(.extra_semi, tok);
805 continue;
806 }
807 try p.err(.expected_external_decl);
808 p.tok_i += 1;
809 }
810 if (p.tentative_defs.count() > 0) {
811 try p.diagnoseIncompleteDefinitions();
812 }
813
814 const root_decls = try p.decl_buf.toOwnedSlice();
815 errdefer pp.comp.gpa.free(root_decls);
816 if (root_decls.len == 0) {
817 try p.errTok(.empty_translation_unit, p.tok_i - 1);
818 }
819 pp.comp.pragmaEvent(.after_parse);
820
821 const data = try p.data.toOwnedSlice();
822 errdefer pp.comp.gpa.free(data);
823 return Tree{
824 .comp = pp.comp,
825 .tokens = pp.tokens.slice(),
826 .arena = arena,
827 .generated = pp.comp.generated_buf.items,
828 .nodes = p.nodes.toOwnedSlice(),
829 .data = data,
830 .root_decls = root_decls,
831 .value_map = p.value_map,
832 };
833}
834
835fn skipToPragmaSentinel(p: *Parser) void {
836 while (true) : (p.tok_i += 1) {
837 if (p.tok_ids[p.tok_i] == .nl) return;
838 if (p.tok_ids[p.tok_i] == .eof) {
839 p.tok_i -= 1;
840 return;
841 }
842 }
843}
844
845fn parseOrNextDecl(p: *Parser, comptime func: fn (*Parser) Error!bool) Compilation.Error!bool {
846 return func(p) catch |er| switch (er) {
847 error.ParsingFailed => {
848 p.nextExternDecl();
849 return true;
850 },
851 else => |e| return e,
852 };
853}
854
855fn nextExternDecl(p: *Parser) void {
856 var parens: u32 = 0;
857 while (true) : (p.tok_i += 1) {
858 switch (p.tok_ids[p.tok_i]) {
859 .l_paren, .l_brace, .l_bracket => parens += 1,
860 .r_paren, .r_brace, .r_bracket => if (parens != 0) {
861 parens -= 1;
862 },
863 .keyword_typedef,
864 .keyword_extern,
865 .keyword_static,
866 .keyword_auto,
867 .keyword_register,
868 .keyword_thread_local,
869 .keyword_c23_thread_local,
870 .keyword_inline,
871 .keyword_inline1,
872 .keyword_inline2,
873 .keyword_noreturn,
874 .keyword_void,
875 .keyword_bool,
876 .keyword_c23_bool,
877 .keyword_char,
878 .keyword_short,
879 .keyword_int,
880 .keyword_long,
881 .keyword_signed,
882 .keyword_signed1,
883 .keyword_signed2,
884 .keyword_unsigned,
885 .keyword_float,
886 .keyword_double,
887 .keyword_complex,
888 .keyword_atomic,
889 .keyword_enum,
890 .keyword_struct,
891 .keyword_union,
892 .keyword_alignas,
893 .keyword_c23_alignas,
894 .identifier,
895 .extended_identifier,
896 .keyword_typeof,
897 .keyword_typeof1,
898 .keyword_typeof2,
899 .keyword_typeof_unqual,
900 .keyword_extension,
901 .keyword_bit_int,
902 => if (parens == 0) return,
903 .keyword_pragma => p.skipToPragmaSentinel(),
904 .eof => return,
905 .semicolon => if (parens == 0) {
906 p.tok_i += 1;
907 return;
908 },
909 else => {},
910 }
911 }
912}
913
914fn skipTo(p: *Parser, id: Token.Id) void {
915 var parens: u32 = 0;
916 while (true) : (p.tok_i += 1) {
917 if (p.tok_ids[p.tok_i] == id and parens == 0) {
918 p.tok_i += 1;
919 return;
920 }
921 switch (p.tok_ids[p.tok_i]) {
922 .l_paren, .l_brace, .l_bracket => parens += 1,
923 .r_paren, .r_brace, .r_bracket => if (parens != 0) {
924 parens -= 1;
925 },
926 .keyword_pragma => p.skipToPragmaSentinel(),
927 .eof => return,
928 else => {},
929 }
930 }
931}
932
933/// Called after a typedef is defined
934fn typedefDefined(p: *Parser, name: StringId, ty: Type) void {
935 if (name == p.string_ids.file) {
936 p.comp.types.file = ty;
937 } else if (name == p.string_ids.jmp_buf) {
938 p.comp.types.jmp_buf = ty;
939 } else if (name == p.string_ids.sigjmp_buf) {
940 p.comp.types.sigjmp_buf = ty;
941 } else if (name == p.string_ids.ucontext_t) {
942 p.comp.types.ucontext_t = ty;
943 }
944}
945
946// ====== declarations ======
947
948/// decl
949/// : declSpec (initDeclarator ( ',' initDeclarator)*)? ';'
950/// | declSpec declarator decl* compoundStmt
951fn decl(p: *Parser) Error!bool {
952 _ = try p.pragma();
953 const first_tok = p.tok_i;
954 const attr_buf_top = p.attr_buf.len;
955 defer p.attr_buf.len = attr_buf_top;
956
957 try p.attributeSpecifier();
958
959 var decl_spec = if (try p.declSpec()) |some| some else blk: {
960 if (p.func.ty != null) {
961 p.tok_i = first_tok;
962 return false;
963 }
964 switch (p.tok_ids[first_tok]) {
965 .asterisk, .l_paren, .identifier, .extended_identifier => {},
966 else => if (p.tok_i != first_tok) {
967 try p.err(.expected_ident_or_l_paren);
968 return error.ParsingFailed;
969 } else return false,
970 }
971 var spec: Type.Builder = .{};
972 break :blk DeclSpec{ .ty = try spec.finish(p) };
973 };
974 if (decl_spec.noreturn) |tok| {
975 const attr = Attribute{ .tag = .noreturn, .args = .{ .noreturn = .{} }, .syntax = .keyword };
976 try p.attr_buf.append(p.gpa, .{ .attr = attr, .tok = tok });
977 }
978 var init_d = (try p.initDeclarator(&decl_spec, attr_buf_top)) orelse {
979 _ = try p.expectToken(.semicolon);
980 if (decl_spec.ty.is(.@"enum") or
981 (decl_spec.ty.isRecord() and !decl_spec.ty.isAnonymousRecord(p.comp) and
982 !decl_spec.ty.isTypeof())) // we follow GCC and clang's behavior here
983 {
984 const specifier = decl_spec.ty.canonicalize(.standard).specifier;
985 const attrs = p.attr_buf.items(.attr)[attr_buf_top..];
986 const toks = p.attr_buf.items(.tok)[attr_buf_top..];
987 for (attrs, toks) |attr, tok| {
988 try p.errExtra(.ignored_record_attr, tok, .{
989 .ignored_record_attr = .{ .tag = attr.tag, .specifier = switch (specifier) {
990 .@"enum" => .@"enum",
991 .@"struct" => .@"struct",
992 .@"union" => .@"union",
993 else => unreachable,
994 } },
995 });
996 }
997 return true;
998 }
999
1000 try p.errTok(.missing_declaration, first_tok);
1001 return true;
1002 };
1003
1004 // Check for function definition.
1005 if (init_d.d.func_declarator != null and init_d.initializer.node == .none and init_d.d.ty.isFunc()) fn_def: {
1006 if (decl_spec.auto_type) |tok_i| {
1007 try p.errStr(.auto_type_not_allowed, tok_i, "function return type");
1008 return error.ParsingFailed;
1009 }
1010
1011 switch (p.tok_ids[p.tok_i]) {
1012 .comma, .semicolon => break :fn_def,
1013 .l_brace => {},
1014 else => if (init_d.d.old_style_func == null) {
1015 try p.err(.expected_fn_body);
1016 return true;
1017 },
1018 }
1019 if (p.func.ty != null) try p.err(.func_not_in_root);
1020
1021 const node = try p.addNode(undefined); // reserve space
1022 const interned_declarator_name = try StrInt.intern(p.comp, p.tokSlice(init_d.d.name));
1023 try p.syms.defineSymbol(p, interned_declarator_name, init_d.d.ty, init_d.d.name, node, .{}, false);
1024
1025 const func = p.func;
1026 p.func = .{
1027 .ty = init_d.d.ty,
1028 .name = init_d.d.name,
1029 };
1030 if (interned_declarator_name == p.string_ids.main_id and !init_d.d.ty.returnType().is(.int)) {
1031 try p.errTok(.main_return_type, init_d.d.name);
1032 }
1033 defer p.func = func;
1034
1035 try p.syms.pushScope(p);
1036 defer p.syms.popScope();
1037
1038 // Collect old style parameter declarations.
1039 if (init_d.d.old_style_func != null) {
1040 var base_ty = init_d.d.ty.base();
1041 base_ty.specifier = .func;
1042
1043 const param_buf_top = p.param_buf.items.len;
1044 defer p.param_buf.items.len = param_buf_top;
1045
1046 param_loop: while (true) {
1047 const param_decl_spec = (try p.declSpec()) orelse break;
1048 if (p.eatToken(.semicolon)) |semi| {
1049 try p.errTok(.missing_declaration, semi);
1050 continue :param_loop;
1051 }
1052
1053 while (true) {
1054 const attr_buf_top_declarator = p.attr_buf.len;
1055 defer p.attr_buf.len = attr_buf_top_declarator;
1056
1057 var d = (try p.declarator(param_decl_spec.ty, .param)) orelse {
1058 try p.errTok(.missing_declaration, first_tok);
1059 _ = try p.expectToken(.semicolon);
1060 continue :param_loop;
1061 };
1062 try p.attributeSpecifier();
1063
1064 if (d.ty.hasIncompleteSize() and !d.ty.is(.void)) try p.errStr(.parameter_incomplete_ty, d.name, try p.typeStr(d.ty));
1065 if (d.ty.isFunc()) {
1066 // Params declared as functions are converted to function pointers.
1067 const elem_ty = try p.arena.create(Type);
1068 elem_ty.* = d.ty;
1069 d.ty = Type{
1070 .specifier = .pointer,
1071 .data = .{ .sub_type = elem_ty },
1072 };
1073 } else if (d.ty.isArray()) {
1074 // params declared as arrays are converted to pointers
1075 d.ty.decayArray();
1076 } else if (d.ty.is(.void)) {
1077 try p.errTok(.invalid_void_param, d.name);
1078 }
1079
1080 // find and correct parameter types
1081 // TODO check for missing declarations and redefinitions
1082 const name_str = p.tokSlice(d.name);
1083 const interned_name = try StrInt.intern(p.comp, name_str);
1084 for (init_d.d.ty.params()) |*param| {
1085 if (param.name == interned_name) {
1086 param.ty = d.ty;
1087 break;
1088 }
1089 } else {
1090 try p.errStr(.parameter_missing, d.name, name_str);
1091 }
1092 d.ty = try Attribute.applyParameterAttributes(p, d.ty, attr_buf_top_declarator, .alignas_on_param);
1093
1094 // bypass redefinition check to avoid duplicate errors
1095 try p.syms.define(p.gpa, .{
1096 .kind = .def,
1097 .name = interned_name,
1098 .tok = d.name,
1099 .ty = d.ty,
1100 .val = .{},
1101 });
1102 if (p.eatToken(.comma) == null) break;
1103 }
1104 _ = try p.expectToken(.semicolon);
1105 }
1106 } else {
1107 for (init_d.d.ty.params()) |param| {
1108 if (param.ty.hasUnboundVLA()) try p.errTok(.unbound_vla, param.name_tok);
1109 if (param.ty.hasIncompleteSize() and !param.ty.is(.void) and param.ty.specifier != .invalid) try p.errStr(.parameter_incomplete_ty, param.name_tok, try p.typeStr(param.ty));
1110
1111 if (param.name == .empty) {
1112 try p.errTok(.omitting_parameter_name, param.name_tok);
1113 continue;
1114 }
1115
1116 // bypass redefinition check to avoid duplicate errors
1117 try p.syms.define(p.gpa, .{
1118 .kind = .def,
1119 .name = param.name,
1120 .tok = param.name_tok,
1121 .ty = param.ty,
1122 .val = .{},
1123 });
1124 }
1125 }
1126
1127 const body = (try p.compoundStmt(true, null)) orelse {
1128 assert(init_d.d.old_style_func != null);
1129 try p.err(.expected_fn_body);
1130 return true;
1131 };
1132 p.nodes.set(@intFromEnum(node), .{
1133 .ty = init_d.d.ty,
1134 .tag = try decl_spec.validateFnDef(p),
1135 .data = .{ .decl = .{ .name = init_d.d.name, .node = body } },
1136 .loc = @enumFromInt(init_d.d.name),
1137 });
1138 try p.decl_buf.append(node);
1139
1140 // check gotos
1141 if (func.ty == null) {
1142 for (p.labels.items) |item| {
1143 if (item == .unresolved_goto)
1144 try p.errStr(.undeclared_label, item.unresolved_goto, p.tokSlice(item.unresolved_goto));
1145 }
1146 if (p.computed_goto_tok) |goto_tok| {
1147 if (!p.contains_address_of_label) try p.errTok(.invalid_computed_goto, goto_tok);
1148 }
1149 p.labels.items.len = 0;
1150 p.label_count = 0;
1151 p.contains_address_of_label = false;
1152 p.computed_goto_tok = null;
1153 }
1154 return true;
1155 }
1156
1157 // Declare all variable/typedef declarators.
1158 var warned_auto = false;
1159 while (true) {
1160 if (init_d.d.old_style_func) |tok_i| try p.errTok(.invalid_old_style_params, tok_i);
1161 const tag = try decl_spec.validate(p, &init_d.d.ty, init_d.initializer.node != .none);
1162
1163 const tok = switch (decl_spec.storage_class) {
1164 .auto, .@"extern", .register, .static, .typedef => |tok| tok,
1165 .none => init_d.d.name,
1166 };
1167 const node = try p.addNode(.{
1168 .ty = init_d.d.ty,
1169 .tag = tag,
1170 .data = .{
1171 .decl = .{ .name = init_d.d.name, .node = init_d.initializer.node },
1172 },
1173 .loc = @enumFromInt(tok),
1174 });
1175 try p.decl_buf.append(node);
1176
1177 const interned_name = try StrInt.intern(p.comp, p.tokSlice(init_d.d.name));
1178 if (decl_spec.storage_class == .typedef) {
1179 try p.syms.defineTypedef(p, interned_name, init_d.d.ty, init_d.d.name, node);
1180 p.typedefDefined(interned_name, init_d.d.ty);
1181 } else if (init_d.initializer.node != .none or
1182 (p.func.ty != null and decl_spec.storage_class != .@"extern"))
1183 {
1184 // TODO validate global variable/constexpr initializer comptime known
1185 try p.syms.defineSymbol(
1186 p,
1187 interned_name,
1188 init_d.d.ty,
1189 init_d.d.name,
1190 node,
1191 if (init_d.d.ty.isConst() or decl_spec.constexpr != null) init_d.initializer.val else .{},
1192 decl_spec.constexpr != null,
1193 );
1194 } else {
1195 try p.syms.declareSymbol(p, interned_name, init_d.d.ty, init_d.d.name, node);
1196 }
1197
1198 if (p.eatToken(.comma) == null) break;
1199
1200 if (!warned_auto) {
1201 if (decl_spec.auto_type) |tok_i| {
1202 try p.errTok(.auto_type_requires_single_declarator, tok_i);
1203 warned_auto = true;
1204 }
1205 if (p.comp.langopts.standard.atLeast(.c23) and decl_spec.storage_class == .auto) {
1206 try p.errTok(.c23_auto_single_declarator, decl_spec.storage_class.auto);
1207 warned_auto = true;
1208 }
1209 }
1210
1211 init_d = (try p.initDeclarator(&decl_spec, attr_buf_top)) orelse {
1212 try p.err(.expected_ident_or_l_paren);
1213 continue;
1214 };
1215 }
1216
1217 _ = try p.expectToken(.semicolon);
1218 return true;
1219}
1220
1221fn staticAssertMessage(p: *Parser, cond_node: NodeIndex, message: Result) !?[]const u8 {
1222 const cond_tag = p.nodes.items(.tag)[@intFromEnum(cond_node)];
1223 if (cond_tag != .builtin_types_compatible_p and message.node == .none) return null;
1224
1225 var buf = std.ArrayList(u8).init(p.gpa);
1226 defer buf.deinit();
1227
1228 if (cond_tag == .builtin_types_compatible_p) {
1229 const mapper = p.comp.string_interner.getSlowTypeMapper();
1230 const data = p.nodes.items(.data)[@intFromEnum(cond_node)].bin;
1231
1232 try buf.appendSlice("'__builtin_types_compatible_p(");
1233
1234 const lhs_ty = p.nodes.items(.ty)[@intFromEnum(data.lhs)];
1235 try lhs_ty.print(mapper, p.comp.langopts, buf.writer());
1236 try buf.appendSlice(", ");
1237
1238 const rhs_ty = p.nodes.items(.ty)[@intFromEnum(data.rhs)];
1239 try rhs_ty.print(mapper, p.comp.langopts, buf.writer());
1240
1241 try buf.appendSlice(")'");
1242 }
1243 if (message.node != .none) {
1244 assert(p.nodes.items(.tag)[@intFromEnum(message.node)] == .string_literal_expr);
1245 if (buf.items.len > 0) {
1246 try buf.append(' ');
1247 }
1248 const bytes = p.comp.interner.get(message.val.ref()).bytes;
1249 try buf.ensureUnusedCapacity(bytes.len);
1250 try Value.printString(bytes, message.ty, p.comp, buf.writer());
1251 }
1252 return try p.comp.diagnostics.arena.allocator().dupe(u8, buf.items);
1253}
1254
1255/// staticAssert
1256/// : keyword_static_assert '(' integerConstExpr (',' STRING_LITERAL)? ')' ';'
1257/// | keyword_c23_static_assert '(' integerConstExpr (',' STRING_LITERAL)? ')' ';'
1258fn staticAssert(p: *Parser) Error!bool {
1259 const static_assert = p.eatToken(.keyword_static_assert) orelse p.eatToken(.keyword_c23_static_assert) orelse return false;
1260 const l_paren = try p.expectToken(.l_paren);
1261 const res_token = p.tok_i;
1262 var res = try p.constExpr(.gnu_folding_extension);
1263 const res_node = res.node;
1264 const str = if (p.eatToken(.comma) != null)
1265 switch (p.tok_ids[p.tok_i]) {
1266 .string_literal,
1267 .string_literal_utf_16,
1268 .string_literal_utf_8,
1269 .string_literal_utf_32,
1270 .string_literal_wide,
1271 .unterminated_string_literal,
1272 => try p.stringLiteral(),
1273 else => {
1274 try p.err(.expected_str_literal);
1275 return error.ParsingFailed;
1276 },
1277 }
1278 else
1279 Result{};
1280 try p.expectClosing(l_paren, .r_paren);
1281 _ = try p.expectToken(.semicolon);
1282 if (str.node == .none) {
1283 try p.errTok(.static_assert_missing_message, static_assert);
1284 try p.errStr(.pre_c23_compat, static_assert, "'_Static_assert' with no message");
1285 }
1286
1287 // Array will never be zero; a value of zero for a pointer is a null pointer constant
1288 if ((res.ty.isArray() or res.ty.isPtr()) and !res.val.isZero(p.comp)) {
1289 const err_start = p.comp.diagnostics.list.items.len;
1290 try p.errTok(.const_decl_folded, res_token);
1291 if (res.ty.isPtr() and err_start != p.comp.diagnostics.list.items.len) {
1292 // Don't show the note if the .const_decl_folded diagnostic was not added
1293 try p.errTok(.constant_expression_conversion_not_allowed, res_token);
1294 }
1295 }
1296 try res.boolCast(p, .{ .specifier = .bool }, res_token);
1297 if (res.val.opt_ref == .none) {
1298 if (res.ty.specifier != .invalid) {
1299 try p.errTok(.static_assert_not_constant, res_token);
1300 }
1301 } else {
1302 if (!res.val.toBool(p.comp)) {
1303 if (try p.staticAssertMessage(res_node, str)) |message| {
1304 try p.errStr(.static_assert_failure_message, static_assert, message);
1305 } else {
1306 try p.errTok(.static_assert_failure, static_assert);
1307 }
1308 }
1309 }
1310
1311 const node = try p.addNode(.{
1312 .tag = .static_assert,
1313 .data = .{ .bin = .{
1314 .lhs = res.node,
1315 .rhs = str.node,
1316 } },
1317 .loc = @enumFromInt(static_assert),
1318 });
1319 try p.decl_buf.append(node);
1320 return true;
1321}
1322
1323pub const DeclSpec = struct {
1324 storage_class: union(enum) {
1325 auto: TokenIndex,
1326 @"extern": TokenIndex,
1327 register: TokenIndex,
1328 static: TokenIndex,
1329 typedef: TokenIndex,
1330 none,
1331 } = .none,
1332 thread_local: ?TokenIndex = null,
1333 constexpr: ?TokenIndex = null,
1334 @"inline": ?TokenIndex = null,
1335 noreturn: ?TokenIndex = null,
1336 auto_type: ?TokenIndex = null,
1337 ty: Type,
1338
1339 fn validateParam(d: DeclSpec, p: *Parser, ty: *Type) Error!void {
1340 switch (d.storage_class) {
1341 .none => {},
1342 .register => ty.qual.register = true,
1343 .auto, .@"extern", .static, .typedef => |tok_i| try p.errTok(.invalid_storage_on_param, tok_i),
1344 }
1345 if (d.thread_local) |tok_i| try p.errTok(.threadlocal_non_var, tok_i);
1346 if (d.@"inline") |tok_i| try p.errStr(.func_spec_non_func, tok_i, "inline");
1347 if (d.noreturn) |tok_i| try p.errStr(.func_spec_non_func, tok_i, "_Noreturn");
1348 if (d.constexpr) |tok_i| try p.errTok(.invalid_storage_on_param, tok_i);
1349 if (d.auto_type) |tok_i| {
1350 try p.errStr(.auto_type_not_allowed, tok_i, "function prototype");
1351 ty.* = Type.invalid;
1352 }
1353 }
1354
1355 fn validateFnDef(d: DeclSpec, p: *Parser) Error!Tree.Tag {
1356 switch (d.storage_class) {
1357 .none, .@"extern", .static => {},
1358 .auto, .register, .typedef => |tok_i| try p.errTok(.illegal_storage_on_func, tok_i),
1359 }
1360 if (d.thread_local) |tok_i| try p.errTok(.threadlocal_non_var, tok_i);
1361 if (d.constexpr) |tok_i| try p.errTok(.illegal_storage_on_func, tok_i);
1362
1363 const is_static = d.storage_class == .static;
1364 const is_inline = d.@"inline" != null;
1365 if (is_static) {
1366 if (is_inline) return .inline_static_fn_def;
1367 return .static_fn_def;
1368 } else {
1369 if (is_inline) return .inline_fn_def;
1370 return .fn_def;
1371 }
1372 }
1373
1374 fn validate(d: DeclSpec, p: *Parser, ty: *Type, has_init: bool) Error!Tree.Tag {
1375 const is_static = d.storage_class == .static;
1376 if (ty.isFunc() and d.storage_class != .typedef) {
1377 switch (d.storage_class) {
1378 .none, .@"extern" => {},
1379 .static => |tok_i| if (p.func.ty != null) try p.errTok(.static_func_not_global, tok_i),
1380 .typedef => unreachable,
1381 .auto, .register => |tok_i| try p.errTok(.illegal_storage_on_func, tok_i),
1382 }
1383 if (d.thread_local) |tok_i| try p.errTok(.threadlocal_non_var, tok_i);
1384 if (d.constexpr) |tok_i| try p.errTok(.illegal_storage_on_func, tok_i);
1385
1386 const is_inline = d.@"inline" != null;
1387 if (is_static) {
1388 if (is_inline) return .inline_static_fn_proto;
1389 return .static_fn_proto;
1390 } else {
1391 if (is_inline) return .inline_fn_proto;
1392 return .fn_proto;
1393 }
1394 } else {
1395 if (d.@"inline") |tok_i| try p.errStr(.func_spec_non_func, tok_i, "inline");
1396 // TODO move to attribute validation
1397 if (d.noreturn) |tok_i| try p.errStr(.func_spec_non_func, tok_i, "_Noreturn");
1398 switch (d.storage_class) {
1399 .auto => if (p.func.ty == null and !p.comp.langopts.standard.atLeast(.c23)) {
1400 try p.err(.illegal_storage_on_global);
1401 },
1402 .register => if (p.func.ty == null) try p.err(.illegal_storage_on_global),
1403 .typedef => return .typedef,
1404 else => {},
1405 }
1406 ty.qual.register = d.storage_class == .register;
1407
1408 const is_extern = d.storage_class == .@"extern" and !has_init;
1409 if (d.thread_local != null) {
1410 if (is_static) return .threadlocal_static_var;
1411 if (is_extern) return .threadlocal_extern_var;
1412 return .threadlocal_var;
1413 } else {
1414 if (is_static) return .static_var;
1415 if (is_extern) return .extern_var;
1416 return .@"var";
1417 }
1418 }
1419 }
1420};
1421
1422/// typeof
1423/// : keyword_typeof '(' typeName ')'
1424/// | keyword_typeof '(' expr ')'
1425fn typeof(p: *Parser) Error!?Type {
1426 var unqual = false;
1427 switch (p.tok_ids[p.tok_i]) {
1428 .keyword_typeof, .keyword_typeof1, .keyword_typeof2 => p.tok_i += 1,
1429 .keyword_typeof_unqual => {
1430 p.tok_i += 1;
1431 unqual = true;
1432 },
1433 else => return null,
1434 }
1435 const l_paren = try p.expectToken(.l_paren);
1436 if (try p.typeName()) |ty| {
1437 try p.expectClosing(l_paren, .r_paren);
1438 if (ty.is(.invalid)) return null;
1439
1440 const typeof_ty = try p.arena.create(Type);
1441 typeof_ty.* = .{
1442 .data = ty.data,
1443 .qual = if (unqual) .{} else ty.qual.inheritFromTypeof(),
1444 .specifier = ty.specifier,
1445 };
1446
1447 return Type{
1448 .data = .{ .sub_type = typeof_ty },
1449 .specifier = .typeof_type,
1450 };
1451 }
1452 const typeof_expr = try p.parseNoEval(expr);
1453 try typeof_expr.expect(p);
1454 try p.expectClosing(l_paren, .r_paren);
1455 // Special case nullptr_t since it's defined as typeof(nullptr)
1456 if (typeof_expr.ty.is(.nullptr_t)) {
1457 return Type{
1458 .specifier = .nullptr_t,
1459 .qual = if (unqual) .{} else typeof_expr.ty.qual.inheritFromTypeof(),
1460 };
1461 } else if (typeof_expr.ty.is(.invalid)) {
1462 return null;
1463 }
1464
1465 const inner = try p.arena.create(Type.Expr);
1466 inner.* = .{
1467 .node = typeof_expr.node,
1468 .ty = .{
1469 .data = typeof_expr.ty.data,
1470 .qual = if (unqual) .{} else typeof_expr.ty.qual.inheritFromTypeof(),
1471 .specifier = typeof_expr.ty.specifier,
1472 .decayed = typeof_expr.ty.decayed,
1473 },
1474 };
1475
1476 return Type{
1477 .data = .{ .expr = inner },
1478 .specifier = .typeof_expr,
1479 .decayed = typeof_expr.ty.decayed,
1480 };
1481}
1482
1483/// declSpec: (storageClassSpec | typeSpec | typeQual | funcSpec | alignSpec)+
1484/// funcSpec : keyword_inline | keyword_noreturn
1485fn declSpec(p: *Parser) Error!?DeclSpec {
1486 var d: DeclSpec = .{ .ty = .{ .specifier = undefined } };
1487 var spec: Type.Builder = .{};
1488
1489 var combined_auto = !p.comp.langopts.standard.atLeast(.c23);
1490 const start = p.tok_i;
1491 while (true) {
1492 if (!combined_auto and d.storage_class == .auto) {
1493 try spec.combine(p, .c23_auto, d.storage_class.auto);
1494 combined_auto = true;
1495 }
1496 if (try p.storageClassSpec(&d)) continue;
1497 if (try p.typeSpec(&spec)) continue;
1498 const id = p.tok_ids[p.tok_i];
1499 switch (id) {
1500 .keyword_inline, .keyword_inline1, .keyword_inline2 => {
1501 if (d.@"inline" != null) {
1502 try p.errStr(.duplicate_decl_spec, p.tok_i, "inline");
1503 }
1504 d.@"inline" = p.tok_i;
1505 },
1506 .keyword_noreturn => {
1507 if (d.noreturn != null) {
1508 try p.errStr(.duplicate_decl_spec, p.tok_i, "_Noreturn");
1509 }
1510 d.noreturn = p.tok_i;
1511 },
1512 else => break,
1513 }
1514 p.tok_i += 1;
1515 }
1516
1517 if (p.tok_i == start) return null;
1518
1519 d.ty = try spec.finish(p);
1520 d.auto_type = spec.auto_type_tok;
1521 return d;
1522}
1523
1524/// storageClassSpec:
1525/// : keyword_typedef
1526/// | keyword_extern
1527/// | keyword_static
1528/// | keyword_threadlocal
1529/// | keyword_auto
1530/// | keyword_register
1531fn storageClassSpec(p: *Parser, d: *DeclSpec) Error!bool {
1532 const start = p.tok_i;
1533 while (true) {
1534 const id = p.tok_ids[p.tok_i];
1535 switch (id) {
1536 .keyword_typedef,
1537 .keyword_extern,
1538 .keyword_static,
1539 .keyword_auto,
1540 .keyword_register,
1541 => {
1542 if (d.storage_class != .none) {
1543 try p.errStr(.multiple_storage_class, p.tok_i, @tagName(d.storage_class));
1544 return error.ParsingFailed;
1545 }
1546 if (d.thread_local != null) {
1547 switch (id) {
1548 .keyword_extern, .keyword_static => {},
1549 else => try p.errStr(.cannot_combine_spec, p.tok_i, id.lexeme().?),
1550 }
1551 if (d.constexpr) |tok| try p.errStr(.cannot_combine_spec, p.tok_i, p.tok_ids[tok].lexeme().?);
1552 }
1553 if (d.constexpr != null) {
1554 switch (id) {
1555 .keyword_auto, .keyword_register, .keyword_static => {},
1556 else => try p.errStr(.cannot_combine_spec, p.tok_i, id.lexeme().?),
1557 }
1558 if (d.thread_local) |tok| try p.errStr(.cannot_combine_spec, p.tok_i, p.tok_ids[tok].lexeme().?);
1559 }
1560 switch (id) {
1561 .keyword_typedef => d.storage_class = .{ .typedef = p.tok_i },
1562 .keyword_extern => d.storage_class = .{ .@"extern" = p.tok_i },
1563 .keyword_static => d.storage_class = .{ .static = p.tok_i },
1564 .keyword_auto => d.storage_class = .{ .auto = p.tok_i },
1565 .keyword_register => d.storage_class = .{ .register = p.tok_i },
1566 else => unreachable,
1567 }
1568 },
1569 .keyword_thread_local,
1570 .keyword_c23_thread_local,
1571 => {
1572 if (d.thread_local != null) {
1573 try p.errStr(.duplicate_decl_spec, p.tok_i, id.lexeme().?);
1574 }
1575 if (d.constexpr) |tok| try p.errStr(.cannot_combine_spec, p.tok_i, p.tok_ids[tok].lexeme().?);
1576 switch (d.storage_class) {
1577 .@"extern", .none, .static => {},
1578 else => try p.errStr(.cannot_combine_spec, p.tok_i, @tagName(d.storage_class)),
1579 }
1580 d.thread_local = p.tok_i;
1581 },
1582 .keyword_constexpr => {
1583 if (d.constexpr != null) {
1584 try p.errStr(.duplicate_decl_spec, p.tok_i, id.lexeme().?);
1585 }
1586 if (d.thread_local) |tok| try p.errStr(.cannot_combine_spec, p.tok_i, p.tok_ids[tok].lexeme().?);
1587 switch (d.storage_class) {
1588 .auto, .register, .none, .static => {},
1589 else => try p.errStr(.cannot_combine_spec, p.tok_i, @tagName(d.storage_class)),
1590 }
1591 d.constexpr = p.tok_i;
1592 },
1593 else => break,
1594 }
1595 p.tok_i += 1;
1596 }
1597 return p.tok_i != start;
1598}
1599
1600const InitDeclarator = struct { d: Declarator, initializer: Result = .{} };
1601
1602/// attribute
1603/// : attrIdentifier
1604/// | attrIdentifier '(' identifier ')'
1605/// | attrIdentifier '(' identifier (',' expr)+ ')'
1606/// | attrIdentifier '(' (expr (',' expr)*)? ')'
1607fn attribute(p: *Parser, kind: Attribute.Kind, namespace: ?[]const u8) Error!?TentativeAttribute {
1608 const name_tok = p.tok_i;
1609 switch (p.tok_ids[p.tok_i]) {
1610 .keyword_const, .keyword_const1, .keyword_const2 => p.tok_i += 1,
1611 else => _ = try p.expectIdentifier(),
1612 }
1613 const name = p.tokSlice(name_tok);
1614
1615 const attr = Attribute.fromString(kind, namespace, name) orelse {
1616 const tag: Diagnostics.Tag = if (kind == .declspec) .declspec_attr_not_supported else .unknown_attribute;
1617 try p.errStr(tag, name_tok, name);
1618 if (p.eatToken(.l_paren)) |_| p.skipTo(.r_paren);
1619 return null;
1620 };
1621
1622 const required_count = Attribute.requiredArgCount(attr);
1623 var arguments = Attribute.initArguments(attr, name_tok);
1624 var arg_idx: u32 = 0;
1625
1626 switch (p.tok_ids[p.tok_i]) {
1627 .comma, .r_paren => {}, // will be consumed in attributeList
1628 .l_paren => blk: {
1629 p.tok_i += 1;
1630 if (p.eatToken(.r_paren)) |_| break :blk;
1631
1632 if (Attribute.wantsIdentEnum(attr)) {
1633 if (try p.eatIdentifier()) |ident| {
1634 if (Attribute.diagnoseIdent(attr, &arguments, p.tokSlice(ident))) |msg| {
1635 try p.errExtra(msg.tag, ident, msg.extra);
1636 p.skipTo(.r_paren);
1637 return error.ParsingFailed;
1638 }
1639 } else {
1640 try p.errExtra(.attribute_requires_identifier, name_tok, .{ .str = name });
1641 return error.ParsingFailed;
1642 }
1643 } else {
1644 const arg_start = p.tok_i;
1645 var first_expr = try p.assignExpr();
1646 try first_expr.expect(p);
1647 if (try p.diagnose(attr, &arguments, arg_idx, first_expr)) |msg| {
1648 try p.errExtra(msg.tag, arg_start, msg.extra);
1649 p.skipTo(.r_paren);
1650 return error.ParsingFailed;
1651 }
1652 }
1653 arg_idx += 1;
1654 while (p.eatToken(.r_paren) == null) : (arg_idx += 1) {
1655 _ = try p.expectToken(.comma);
1656
1657 const arg_start = p.tok_i;
1658 var arg_expr = try p.assignExpr();
1659 try arg_expr.expect(p);
1660 if (try p.diagnose(attr, &arguments, arg_idx, arg_expr)) |msg| {
1661 try p.errExtra(msg.tag, arg_start, msg.extra);
1662 p.skipTo(.r_paren);
1663 return error.ParsingFailed;
1664 }
1665 }
1666 },
1667 else => {},
1668 }
1669 if (arg_idx < required_count) {
1670 try p.errExtra(.attribute_not_enough_args, name_tok, .{ .attr_arg_count = .{ .attribute = attr, .expected = required_count } });
1671 return error.ParsingFailed;
1672 }
1673 return TentativeAttribute{ .attr = .{ .tag = attr, .args = arguments, .syntax = kind.toSyntax() }, .tok = name_tok };
1674}
1675
1676fn diagnose(p: *Parser, attr: Attribute.Tag, arguments: *Attribute.Arguments, arg_idx: u32, res: Result) !?Diagnostics.Message {
1677 if (Attribute.wantsAlignment(attr, arg_idx)) {
1678 return Attribute.diagnoseAlignment(attr, arguments, arg_idx, res, p);
1679 }
1680 const node = p.nodes.get(@intFromEnum(res.node));
1681 return Attribute.diagnose(attr, arguments, arg_idx, res, node, p);
1682}
1683
1684/// attributeList : (attribute (',' attribute)*)?
1685fn gnuAttributeList(p: *Parser) Error!void {
1686 if (p.tok_ids[p.tok_i] == .r_paren) return;
1687
1688 if (try p.attribute(.gnu, null)) |attr| try p.attr_buf.append(p.gpa, attr);
1689 while (p.tok_ids[p.tok_i] != .r_paren) {
1690 _ = try p.expectToken(.comma);
1691 if (try p.attribute(.gnu, null)) |attr| try p.attr_buf.append(p.gpa, attr);
1692 }
1693}
1694
1695fn c23AttributeList(p: *Parser) Error!void {
1696 while (p.tok_ids[p.tok_i] != .r_bracket) {
1697 const namespace_tok = try p.expectIdentifier();
1698 var namespace: ?[]const u8 = null;
1699 if (p.eatToken(.colon_colon)) |_| {
1700 namespace = p.tokSlice(namespace_tok);
1701 } else {
1702 p.tok_i -= 1;
1703 }
1704 if (try p.attribute(.c23, namespace)) |attr| try p.attr_buf.append(p.gpa, attr);
1705 _ = p.eatToken(.comma);
1706 }
1707}
1708
1709fn msvcAttributeList(p: *Parser) Error!void {
1710 while (p.tok_ids[p.tok_i] != .r_paren) {
1711 if (try p.attribute(.declspec, null)) |attr| try p.attr_buf.append(p.gpa, attr);
1712 _ = p.eatToken(.comma);
1713 }
1714}
1715
1716fn c23Attribute(p: *Parser) !bool {
1717 if (!p.comp.langopts.standard.atLeast(.c23)) return false;
1718 const bracket1 = p.eatToken(.l_bracket) orelse return false;
1719 const bracket2 = p.eatToken(.l_bracket) orelse {
1720 p.tok_i -= 1;
1721 return false;
1722 };
1723
1724 try p.c23AttributeList();
1725
1726 _ = try p.expectClosing(bracket2, .r_bracket);
1727 _ = try p.expectClosing(bracket1, .r_bracket);
1728
1729 return true;
1730}
1731
1732fn msvcAttribute(p: *Parser) !bool {
1733 _ = p.eatToken(.keyword_declspec) orelse return false;
1734 const l_paren = try p.expectToken(.l_paren);
1735 try p.msvcAttributeList();
1736 _ = try p.expectClosing(l_paren, .r_paren);
1737
1738 return true;
1739}
1740
1741fn gnuAttribute(p: *Parser) !bool {
1742 switch (p.tok_ids[p.tok_i]) {
1743 .keyword_attribute1, .keyword_attribute2 => p.tok_i += 1,
1744 else => return false,
1745 }
1746 const paren1 = try p.expectToken(.l_paren);
1747 const paren2 = try p.expectToken(.l_paren);
1748
1749 try p.gnuAttributeList();
1750
1751 _ = try p.expectClosing(paren2, .r_paren);
1752 _ = try p.expectClosing(paren1, .r_paren);
1753 return true;
1754}
1755
1756fn attributeSpecifier(p: *Parser) Error!void {
1757 return attributeSpecifierExtra(p, null);
1758}
1759
1760/// attributeSpecifier : (keyword_attribute '( '(' attributeList ')' ')')*
1761fn attributeSpecifierExtra(p: *Parser, declarator_name: ?TokenIndex) Error!void {
1762 while (true) {
1763 if (try p.gnuAttribute()) continue;
1764 if (try p.c23Attribute()) continue;
1765 const maybe_declspec_tok = p.tok_i;
1766 const attr_buf_top = p.attr_buf.len;
1767 if (try p.msvcAttribute()) {
1768 if (declarator_name) |name_tok| {
1769 try p.errTok(.declspec_not_allowed_after_declarator, maybe_declspec_tok);
1770 try p.errTok(.declarator_name_tok, name_tok);
1771 p.attr_buf.len = attr_buf_top;
1772 }
1773 continue;
1774 }
1775 break;
1776 }
1777}
1778
1779/// initDeclarator : declarator assembly? attributeSpecifier? ('=' initializer)?
1780fn initDeclarator(p: *Parser, decl_spec: *DeclSpec, attr_buf_top: usize) Error!?InitDeclarator {
1781 const this_attr_buf_top = p.attr_buf.len;
1782 defer p.attr_buf.len = this_attr_buf_top;
1783
1784 var init_d = InitDeclarator{
1785 .d = (try p.declarator(decl_spec.ty, .normal)) orelse return null,
1786 };
1787
1788 if (decl_spec.ty.is(.c23_auto) and !init_d.d.ty.is(.c23_auto)) {
1789 try p.errTok(.c23_auto_plain_declarator, decl_spec.storage_class.auto);
1790 return error.ParsingFailed;
1791 }
1792
1793 try p.attributeSpecifierExtra(init_d.d.name);
1794 _ = try p.assembly(.decl_label);
1795 try p.attributeSpecifierExtra(init_d.d.name);
1796
1797 var apply_var_attributes = false;
1798 if (decl_spec.storage_class == .typedef) {
1799 if (decl_spec.auto_type) |tok_i| {
1800 try p.errStr(.auto_type_not_allowed, tok_i, "typedef");
1801 return error.ParsingFailed;
1802 }
1803 init_d.d.ty = try Attribute.applyTypeAttributes(p, init_d.d.ty, attr_buf_top, null);
1804 } else if (init_d.d.ty.isFunc()) {
1805 init_d.d.ty = try Attribute.applyFunctionAttributes(p, init_d.d.ty, attr_buf_top);
1806 } else {
1807 apply_var_attributes = true;
1808 }
1809 const c23_auto = init_d.d.ty.is(.c23_auto);
1810 const auto_type = init_d.d.ty.is(.auto_type);
1811
1812 if (p.eatToken(.equal)) |eq| init: {
1813 if (decl_spec.storage_class == .typedef or
1814 (init_d.d.func_declarator != null and init_d.d.ty.isFunc()))
1815 {
1816 try p.errTok(.illegal_initializer, eq);
1817 } else if (init_d.d.ty.is(.variable_len_array)) {
1818 try p.errTok(.vla_init, eq);
1819 } else if (decl_spec.storage_class == .@"extern") {
1820 try p.err(.extern_initializer);
1821 decl_spec.storage_class = .none;
1822 }
1823
1824 if (init_d.d.ty.hasIncompleteSize() and !init_d.d.ty.is(.incomplete_array)) {
1825 try p.errStr(.variable_incomplete_ty, init_d.d.name, try p.typeStr(init_d.d.ty));
1826 return error.ParsingFailed;
1827 }
1828 if (p.tok_ids[p.tok_i] == .l_brace and init_d.d.ty.is(.c23_auto)) {
1829 try p.errTok(.c23_auto_scalar_init, decl_spec.storage_class.auto);
1830 return error.ParsingFailed;
1831 }
1832
1833 try p.syms.pushScope(p);
1834 defer p.syms.popScope();
1835
1836 const interned_name = try StrInt.intern(p.comp, p.tokSlice(init_d.d.name));
1837 try p.syms.declareSymbol(p, interned_name, init_d.d.ty, init_d.d.name, .none);
1838 if (c23_auto or auto_type) {
1839 p.auto_type_decl_name = interned_name;
1840 }
1841 defer p.auto_type_decl_name = .empty;
1842
1843 var init_list_expr = try p.initializer(init_d.d.ty);
1844 init_d.initializer = init_list_expr;
1845 if (!init_list_expr.ty.isArray()) break :init;
1846 if (init_d.d.ty.is(.incomplete_array)) {
1847 init_d.d.ty.setIncompleteArrayLen(init_list_expr.ty.arrayLen() orelse break :init);
1848 }
1849 }
1850
1851 const name = init_d.d.name;
1852 if (auto_type or c23_auto) {
1853 if (init_d.initializer.node == .none) {
1854 init_d.d.ty = Type.invalid;
1855 if (c23_auto) {
1856 try p.errStr(.c32_auto_requires_initializer, decl_spec.storage_class.auto, p.tokSlice(name));
1857 } else {
1858 try p.errStr(.auto_type_requires_initializer, name, p.tokSlice(name));
1859 }
1860 return init_d;
1861 } else {
1862 init_d.d.ty.specifier = init_d.initializer.ty.specifier;
1863 init_d.d.ty.data = init_d.initializer.ty.data;
1864 init_d.d.ty.decayed = init_d.initializer.ty.decayed;
1865 }
1866 }
1867 if (apply_var_attributes) {
1868 init_d.d.ty = try Attribute.applyVariableAttributes(p, init_d.d.ty, attr_buf_top, null);
1869 }
1870 if (decl_spec.storage_class != .typedef and init_d.d.ty.hasIncompleteSize()) incomplete: {
1871 const specifier = init_d.d.ty.canonicalize(.standard).specifier;
1872 if (decl_spec.storage_class == .@"extern") switch (specifier) {
1873 .@"struct", .@"union", .@"enum" => break :incomplete,
1874 .incomplete_array => {
1875 init_d.d.ty.decayArray();
1876 break :incomplete;
1877 },
1878 else => {},
1879 };
1880 // if there was an initializer expression it must have contained an error
1881 if (init_d.initializer.node != .none) break :incomplete;
1882
1883 if (p.func.ty == null) {
1884 if (specifier == .incomplete_array) {
1885 // TODO properly check this after finishing parsing
1886 try p.errStr(.tentative_array, name, try p.typeStr(init_d.d.ty));
1887 break :incomplete;
1888 } else if (init_d.d.ty.getRecord()) |record| {
1889 _ = try p.tentative_defs.getOrPutValue(p.gpa, record.name, init_d.d.name);
1890 break :incomplete;
1891 } else if (init_d.d.ty.get(.@"enum")) |en| {
1892 _ = try p.tentative_defs.getOrPutValue(p.gpa, en.data.@"enum".name, init_d.d.name);
1893 break :incomplete;
1894 }
1895 }
1896 try p.errStr(.variable_incomplete_ty, name, try p.typeStr(init_d.d.ty));
1897 }
1898 return init_d;
1899}
1900
1901/// typeSpec
1902/// : keyword_void
1903/// | keyword_auto_type
1904/// | keyword_char
1905/// | keyword_short
1906/// | keyword_int
1907/// | keyword_long
1908/// | keyword_float
1909/// | keyword_double
1910/// | keyword_signed
1911/// | keyword_signed1
1912/// | keyword_signed2
1913/// | keyword_unsigned
1914/// | keyword_bool
1915/// | keyword_c23_bool
1916/// | keyword_complex
1917/// | atomicTypeSpec
1918/// | recordSpec
1919/// | enumSpec
1920/// | typedef // IDENTIFIER
1921/// | typeof
1922/// | keyword_bit_int '(' integerConstExpr ')'
1923/// atomicTypeSpec : keyword_atomic '(' typeName ')'
1924/// alignSpec
1925/// : keyword_alignas '(' typeName ')'
1926/// | keyword_alignas '(' integerConstExpr ')'
1927/// | keyword_c23_alignas '(' typeName ')'
1928/// | keyword_c23_alignas '(' integerConstExpr ')'
1929fn typeSpec(p: *Parser, ty: *Type.Builder) Error!bool {
1930 const start = p.tok_i;
1931 while (true) {
1932 try p.attributeSpecifier();
1933
1934 if (try p.typeof()) |inner_ty| {
1935 try ty.combineFromTypeof(p, inner_ty, start);
1936 continue;
1937 }
1938 if (try p.typeQual(&ty.qual)) continue;
1939 switch (p.tok_ids[p.tok_i]) {
1940 .keyword_void => try ty.combine(p, .void, p.tok_i),
1941 .keyword_auto_type => {
1942 try p.errTok(.auto_type_extension, p.tok_i);
1943 try ty.combine(p, .auto_type, p.tok_i);
1944 },
1945 .keyword_bool, .keyword_c23_bool => try ty.combine(p, .bool, p.tok_i),
1946 .keyword_int8, .keyword_int8_2, .keyword_char => try ty.combine(p, .char, p.tok_i),
1947 .keyword_int16, .keyword_int16_2, .keyword_short => try ty.combine(p, .short, p.tok_i),
1948 .keyword_int32, .keyword_int32_2, .keyword_int => try ty.combine(p, .int, p.tok_i),
1949 .keyword_long => try ty.combine(p, .long, p.tok_i),
1950 .keyword_int64, .keyword_int64_2 => try ty.combine(p, .long_long, p.tok_i),
1951 .keyword_int128 => try ty.combine(p, .int128, p.tok_i),
1952 .keyword_signed, .keyword_signed1, .keyword_signed2 => try ty.combine(p, .signed, p.tok_i),
1953 .keyword_unsigned => try ty.combine(p, .unsigned, p.tok_i),
1954 .keyword_fp16 => try ty.combine(p, .fp16, p.tok_i),
1955 .keyword_float16 => try ty.combine(p, .float16, p.tok_i),
1956 .keyword_float => try ty.combine(p, .float, p.tok_i),
1957 .keyword_double => try ty.combine(p, .double, p.tok_i),
1958 .keyword_complex => try ty.combine(p, .complex, p.tok_i),
1959 .keyword_float128_1, .keyword_float128_2 => {
1960 if (!p.comp.hasFloat128()) {
1961 try p.errStr(.type_not_supported_on_target, p.tok_i, p.tok_ids[p.tok_i].lexeme().?);
1962 }
1963 try ty.combine(p, .float128, p.tok_i);
1964 },
1965 .keyword_atomic => {
1966 const atomic_tok = p.tok_i;
1967 p.tok_i += 1;
1968 const l_paren = p.eatToken(.l_paren) orelse {
1969 // _Atomic qualifier not _Atomic(typeName)
1970 p.tok_i = atomic_tok;
1971 break;
1972 };
1973 const inner_ty = (try p.typeName()) orelse {
1974 try p.err(.expected_type);
1975 return error.ParsingFailed;
1976 };
1977 try p.expectClosing(l_paren, .r_paren);
1978
1979 const new_spec = Type.Builder.fromType(inner_ty);
1980 try ty.combine(p, new_spec, atomic_tok);
1981
1982 if (ty.qual.atomic != null)
1983 try p.errStr(.duplicate_decl_spec, atomic_tok, "atomic")
1984 else
1985 ty.qual.atomic = atomic_tok;
1986 continue;
1987 },
1988 .keyword_alignas,
1989 .keyword_c23_alignas,
1990 => {
1991 const align_tok = p.tok_i;
1992 p.tok_i += 1;
1993 const l_paren = try p.expectToken(.l_paren);
1994 const typename_start = p.tok_i;
1995 if (try p.typeName()) |inner_ty| {
1996 if (!inner_ty.alignable()) {
1997 try p.errStr(.invalid_alignof, typename_start, try p.typeStr(inner_ty));
1998 }
1999 const alignment = Attribute.Alignment{ .requested = inner_ty.alignof(p.comp) };
2000 try p.attr_buf.append(p.gpa, .{
2001 .attr = .{ .tag = .aligned, .args = .{
2002 .aligned = .{ .alignment = alignment, .__name_tok = align_tok },
2003 }, .syntax = .keyword },
2004 .tok = align_tok,
2005 });
2006 } else {
2007 const arg_start = p.tok_i;
2008 const res = try p.integerConstExpr(.no_const_decl_folding);
2009 if (!res.val.isZero(p.comp)) {
2010 var args = Attribute.initArguments(.aligned, align_tok);
2011 if (try p.diagnose(.aligned, &args, 0, res)) |msg| {
2012 try p.errExtra(msg.tag, arg_start, msg.extra);
2013 p.skipTo(.r_paren);
2014 return error.ParsingFailed;
2015 }
2016 args.aligned.alignment.?.node = res.node;
2017 try p.attr_buf.append(p.gpa, .{
2018 .attr = .{ .tag = .aligned, .args = args, .syntax = .keyword },
2019 .tok = align_tok,
2020 });
2021 }
2022 }
2023 try p.expectClosing(l_paren, .r_paren);
2024 continue;
2025 },
2026 .keyword_stdcall,
2027 .keyword_stdcall2,
2028 .keyword_thiscall,
2029 .keyword_thiscall2,
2030 .keyword_vectorcall,
2031 .keyword_vectorcall2,
2032 => try p.attr_buf.append(p.gpa, .{
2033 .attr = .{ .tag = .calling_convention, .args = .{
2034 .calling_convention = .{ .cc = switch (p.tok_ids[p.tok_i]) {
2035 .keyword_stdcall,
2036 .keyword_stdcall2,
2037 => .stdcall,
2038 .keyword_thiscall,
2039 .keyword_thiscall2,
2040 => .thiscall,
2041 .keyword_vectorcall,
2042 .keyword_vectorcall2,
2043 => .vectorcall,
2044 else => unreachable,
2045 } },
2046 }, .syntax = .keyword },
2047 .tok = p.tok_i,
2048 }),
2049 .keyword_struct, .keyword_union => {
2050 const tag_tok = p.tok_i;
2051 const record_ty = try p.recordSpec();
2052 try ty.combine(p, Type.Builder.fromType(record_ty), tag_tok);
2053 continue;
2054 },
2055 .keyword_enum => {
2056 const tag_tok = p.tok_i;
2057 const enum_ty = try p.enumSpec();
2058 try ty.combine(p, Type.Builder.fromType(enum_ty), tag_tok);
2059 continue;
2060 },
2061 .identifier, .extended_identifier => {
2062 var interned_name = try StrInt.intern(p.comp, p.tokSlice(p.tok_i));
2063 var declspec_found = false;
2064
2065 if (interned_name == p.string_ids.declspec_id) {
2066 try p.errTok(.declspec_not_enabled, p.tok_i);
2067 p.tok_i += 1;
2068 if (p.eatToken(.l_paren)) |_| {
2069 p.skipTo(.r_paren);
2070 continue;
2071 }
2072 declspec_found = true;
2073 }
2074 if (ty.typedef != null) break;
2075 if (declspec_found) {
2076 interned_name = try StrInt.intern(p.comp, p.tokSlice(p.tok_i));
2077 }
2078 const typedef = (try p.syms.findTypedef(p, interned_name, p.tok_i, ty.specifier != .none)) orelse break;
2079 if (!ty.combineTypedef(p, typedef.ty, typedef.tok)) break;
2080 },
2081 .keyword_bit_int => {
2082 try p.err(.bit_int);
2083 const bit_int_tok = p.tok_i;
2084 p.tok_i += 1;
2085 const l_paren = try p.expectToken(.l_paren);
2086 const res = try p.integerConstExpr(.gnu_folding_extension);
2087 try p.expectClosing(l_paren, .r_paren);
2088
2089 var bits: u64 = undefined;
2090 if (res.val.opt_ref == .none) {
2091 try p.errTok(.expected_integer_constant_expr, bit_int_tok);
2092 return error.ParsingFailed;
2093 } else if (res.val.compare(.lte, Value.zero, p.comp)) {
2094 bits = 0;
2095 } else {
2096 bits = res.val.toInt(u64, p.comp) orelse std.math.maxInt(u64);
2097 }
2098
2099 try ty.combine(p, .{ .bit_int = bits }, bit_int_tok);
2100 continue;
2101 },
2102 else => break,
2103 }
2104 // consume single token specifiers here
2105 p.tok_i += 1;
2106 }
2107 return p.tok_i != start;
2108}
2109
2110fn getAnonymousName(p: *Parser, kind_tok: TokenIndex) !StringId {
2111 const loc = p.pp.tokens.items(.loc)[kind_tok];
2112 const source = p.comp.getSource(loc.id);
2113 const line_col = source.lineCol(loc);
2114
2115 const kind_str = switch (p.tok_ids[kind_tok]) {
2116 .keyword_struct, .keyword_union, .keyword_enum => p.tokSlice(kind_tok),
2117 else => "record field",
2118 };
2119
2120 const str = try std.fmt.allocPrint(
2121 p.arena,
2122 "(anonymous {s} at {s}:{d}:{d})",
2123 .{ kind_str, source.path, line_col.line_no, line_col.col },
2124 );
2125 return StrInt.intern(p.comp, str);
2126}
2127
2128/// recordSpec
2129/// : (keyword_struct | keyword_union) IDENTIFIER? { recordDecl* }
2130/// | (keyword_struct | keyword_union) IDENTIFIER
2131fn recordSpec(p: *Parser) Error!Type {
2132 const starting_pragma_pack = p.pragma_pack;
2133 const kind_tok = p.tok_i;
2134 const is_struct = p.tok_ids[kind_tok] == .keyword_struct;
2135 p.tok_i += 1;
2136 const attr_buf_top = p.attr_buf.len;
2137 defer p.attr_buf.len = attr_buf_top;
2138 try p.attributeSpecifier();
2139
2140 const maybe_ident = try p.eatIdentifier();
2141 const l_brace = p.eatToken(.l_brace) orelse {
2142 const ident = maybe_ident orelse {
2143 try p.err(.ident_or_l_brace);
2144 return error.ParsingFailed;
2145 };
2146 // check if this is a reference to a previous type
2147 const interned_name = try StrInt.intern(p.comp, p.tokSlice(ident));
2148 if (try p.syms.findTag(p, interned_name, p.tok_ids[kind_tok], ident, p.tok_ids[p.tok_i])) |prev| {
2149 return prev.ty;
2150 } else {
2151 // this is a forward declaration, create a new record Type.
2152 const record_ty = try Type.Record.create(p.arena, interned_name);
2153 const ty = try Attribute.applyTypeAttributes(p, .{
2154 .specifier = if (is_struct) .@"struct" else .@"union",
2155 .data = .{ .record = record_ty },
2156 }, attr_buf_top, null);
2157 try p.syms.define(p.gpa, .{
2158 .kind = if (is_struct) .@"struct" else .@"union",
2159 .name = interned_name,
2160 .tok = ident,
2161 .ty = ty,
2162 .val = .{},
2163 });
2164 try p.decl_buf.append(try p.addNode(.{
2165 .tag = if (is_struct) .struct_forward_decl else .union_forward_decl,
2166 .ty = ty,
2167 .data = .{ .decl_ref = ident },
2168 .loc = @enumFromInt(ident),
2169 }));
2170 return ty;
2171 }
2172 };
2173
2174 var done = false;
2175 errdefer if (!done) p.skipTo(.r_brace);
2176
2177 // Get forward declared type or create a new one
2178 var defined = false;
2179 const record_ty: *Type.Record = if (maybe_ident) |ident| record_ty: {
2180 const ident_str = p.tokSlice(ident);
2181 const interned_name = try StrInt.intern(p.comp, ident_str);
2182 if (try p.syms.defineTag(p, interned_name, p.tok_ids[kind_tok], ident)) |prev| {
2183 if (!prev.ty.hasIncompleteSize()) {
2184 // if the record isn't incomplete, this is a redefinition
2185 try p.errStr(.redefinition, ident, ident_str);
2186 try p.errTok(.previous_definition, prev.tok);
2187 } else {
2188 defined = true;
2189 break :record_ty prev.ty.get(if (is_struct) .@"struct" else .@"union").?.data.record;
2190 }
2191 }
2192 break :record_ty try Type.Record.create(p.arena, interned_name);
2193 } else try Type.Record.create(p.arena, try p.getAnonymousName(kind_tok));
2194
2195 // Initially create ty as a regular non-attributed type, since attributes for a record
2196 // can be specified after the closing rbrace, which we haven't encountered yet.
2197 var ty = Type{
2198 .specifier = if (is_struct) .@"struct" else .@"union",
2199 .data = .{ .record = record_ty },
2200 };
2201
2202 // declare a symbol for the type
2203 // We need to replace the symbol's type if it has attributes
2204 if (maybe_ident != null and !defined) {
2205 try p.syms.define(p.gpa, .{
2206 .kind = if (is_struct) .@"struct" else .@"union",
2207 .name = record_ty.name,
2208 .tok = maybe_ident.?,
2209 .ty = ty,
2210 .val = .{},
2211 });
2212 }
2213
2214 // reserve space for this record
2215 try p.decl_buf.append(.none);
2216 const decl_buf_top = p.decl_buf.items.len;
2217 const record_buf_top = p.record_buf.items.len;
2218 errdefer p.decl_buf.items.len = decl_buf_top - 1;
2219 defer {
2220 p.decl_buf.items.len = decl_buf_top;
2221 p.record_buf.items.len = record_buf_top;
2222 }
2223
2224 const old_record = p.record;
2225 const old_members = p.record_members.items.len;
2226 const old_field_attr_start = p.field_attr_buf.items.len;
2227 p.record = .{
2228 .kind = p.tok_ids[kind_tok],
2229 .start = p.record_members.items.len,
2230 .field_attr_start = p.field_attr_buf.items.len,
2231 };
2232 defer p.record = old_record;
2233 defer p.record_members.items.len = old_members;
2234 defer p.field_attr_buf.items.len = old_field_attr_start;
2235
2236 try p.recordDecls();
2237
2238 if (p.record.flexible_field) |some| {
2239 if (p.record_buf.items[record_buf_top..].len == 1 and is_struct) {
2240 try p.errTok(.flexible_in_empty, some);
2241 }
2242 }
2243
2244 for (p.record_buf.items[record_buf_top..]) |field| {
2245 if (field.ty.hasIncompleteSize() and !field.ty.is(.incomplete_array)) break;
2246 } else {
2247 record_ty.fields = try p.arena.dupe(Type.Record.Field, p.record_buf.items[record_buf_top..]);
2248 }
2249 const attr_count = p.field_attr_buf.items.len - old_field_attr_start;
2250 const record_decls = p.decl_buf.items[decl_buf_top..];
2251 if (attr_count > 0) {
2252 if (attr_count != record_decls.len) {
2253 // A mismatch here means that non-field decls were parsed. This can happen if there were
2254 // parse errors during attribute parsing. Bail here because if there are any field attributes,
2255 // there must be exactly one per field.
2256 return error.ParsingFailed;
2257 }
2258 const field_attr_slice = p.field_attr_buf.items[old_field_attr_start..];
2259 const duped = try p.arena.dupe([]const Attribute, field_attr_slice);
2260 record_ty.field_attributes = duped.ptr;
2261 }
2262
2263 if (p.record_buf.items.len == record_buf_top) {
2264 try p.errStr(.empty_record, kind_tok, p.tokSlice(kind_tok));
2265 try p.errStr(.empty_record_size, kind_tok, p.tokSlice(kind_tok));
2266 }
2267 try p.expectClosing(l_brace, .r_brace);
2268 done = true;
2269 try p.attributeSpecifier();
2270
2271 ty = try Attribute.applyTypeAttributes(p, .{
2272 .specifier = if (is_struct) .@"struct" else .@"union",
2273 .data = .{ .record = record_ty },
2274 }, attr_buf_top, null);
2275 if (ty.specifier == .attributed and maybe_ident != null) {
2276 const ident_str = p.tokSlice(maybe_ident.?);
2277 const interned_name = try StrInt.intern(p.comp, ident_str);
2278 const ptr = p.syms.getPtr(interned_name, .tags);
2279 ptr.ty = ty;
2280 }
2281
2282 if (!ty.hasIncompleteSize()) {
2283 const pragma_pack_value = switch (p.comp.langopts.emulate) {
2284 .clang => starting_pragma_pack,
2285 .gcc => p.pragma_pack,
2286 // TODO: msvc considers `#pragma pack` on a per-field basis
2287 .msvc => p.pragma_pack,
2288 };
2289 record_layout.compute(record_ty, ty, p.comp, pragma_pack_value) catch |er| switch (er) {
2290 error.Overflow => try p.errStr(.record_too_large, maybe_ident orelse kind_tok, try p.typeStr(ty)),
2291 };
2292 }
2293
2294 // finish by creating a node
2295 var node: Tree.Node = .{
2296 .tag = if (is_struct) .struct_decl_two else .union_decl_two,
2297 .ty = ty,
2298 .data = .{ .two = .{ .none, .none } },
2299 .loc = @enumFromInt(maybe_ident orelse kind_tok),
2300 };
2301 switch (record_decls.len) {
2302 0 => {},
2303 1 => node.data = .{ .two = .{ record_decls[0], .none } },
2304 2 => node.data = .{ .two = .{ record_decls[0], record_decls[1] } },
2305 else => {
2306 node.tag = if (is_struct) .struct_decl else .union_decl;
2307 node.data = .{ .range = try p.addList(record_decls) };
2308 },
2309 }
2310 p.decl_buf.items[decl_buf_top - 1] = try p.addNode(node);
2311 if (p.func.ty == null) {
2312 _ = p.tentative_defs.remove(record_ty.name);
2313 }
2314 return ty;
2315}
2316
2317/// recordDecl
2318/// : specQual (recordDeclarator (',' recordDeclarator)*)? ;
2319/// | staticAssert
2320fn recordDecls(p: *Parser) Error!void {
2321 while (true) {
2322 if (try p.pragma()) continue;
2323 if (try p.parseOrNextDecl(staticAssert)) continue;
2324 if (p.eatToken(.keyword_extension)) |_| {
2325 const saved_extension = p.extension_suppressed;
2326 defer p.extension_suppressed = saved_extension;
2327 p.extension_suppressed = true;
2328
2329 if (try p.parseOrNextDecl(recordDeclarator)) continue;
2330 try p.err(.expected_type);
2331 p.nextExternDecl();
2332 continue;
2333 }
2334 if (try p.parseOrNextDecl(recordDeclarator)) continue;
2335 break;
2336 }
2337}
2338
2339/// recordDeclarator : keyword_extension? declarator (':' integerConstExpr)?
2340fn recordDeclarator(p: *Parser) Error!bool {
2341 const attr_buf_top = p.attr_buf.len;
2342 defer p.attr_buf.len = attr_buf_top;
2343 const base_ty = (try p.specQual()) orelse return false;
2344
2345 try p.attributeSpecifier(); // .record
2346 while (true) {
2347 const this_decl_top = p.attr_buf.len;
2348 defer p.attr_buf.len = this_decl_top;
2349
2350 try p.attributeSpecifier();
2351
2352 // 0 means unnamed
2353 var name_tok: TokenIndex = 0;
2354 var ty = base_ty;
2355 if (ty.is(.auto_type)) {
2356 try p.errStr(.auto_type_not_allowed, p.tok_i, if (p.record.kind == .keyword_struct) "struct member" else "union member");
2357 ty = Type.invalid;
2358 }
2359 var bits_node: NodeIndex = .none;
2360 var bits: ?u32 = null;
2361 const first_tok = p.tok_i;
2362 if (try p.declarator(ty, .record)) |d| {
2363 name_tok = d.name;
2364 ty = d.ty;
2365 }
2366
2367 if (p.eatToken(.colon)) |_| bits: {
2368 const bits_tok = p.tok_i;
2369 const res = try p.integerConstExpr(.gnu_folding_extension);
2370 if (!ty.isInt()) {
2371 try p.errStr(.non_int_bitfield, first_tok, try p.typeStr(ty));
2372 break :bits;
2373 }
2374
2375 if (res.val.opt_ref == .none) {
2376 try p.errTok(.expected_integer_constant_expr, bits_tok);
2377 break :bits;
2378 } else if (res.val.compare(.lt, Value.zero, p.comp)) {
2379 try p.errStr(.negative_bitwidth, first_tok, try res.str(p));
2380 break :bits;
2381 }
2382
2383 // incomplete size error is reported later
2384 const bit_size = ty.bitSizeof(p.comp) orelse break :bits;
2385 const bits_unchecked = res.val.toInt(u32, p.comp) orelse std.math.maxInt(u32);
2386 if (bits_unchecked > bit_size) {
2387 try p.errTok(.bitfield_too_big, name_tok);
2388 break :bits;
2389 } else if (bits_unchecked == 0 and name_tok != 0) {
2390 try p.errTok(.zero_width_named_field, name_tok);
2391 break :bits;
2392 }
2393
2394 bits = bits_unchecked;
2395 bits_node = res.node;
2396 }
2397
2398 try p.attributeSpecifier(); // .record
2399 const to_append = try Attribute.applyFieldAttributes(p, &ty, attr_buf_top);
2400
2401 const any_fields_have_attrs = p.field_attr_buf.items.len > p.record.field_attr_start;
2402
2403 if (any_fields_have_attrs) {
2404 try p.field_attr_buf.append(to_append);
2405 } else {
2406 if (to_append.len > 0) {
2407 const preceding = p.record_members.items.len - p.record.start;
2408 if (preceding > 0) {
2409 try p.field_attr_buf.appendNTimes(&.{}, preceding);
2410 }
2411 try p.field_attr_buf.append(to_append);
2412 }
2413 }
2414
2415 if (name_tok == 0 and bits_node == .none) unnamed: {
2416 if (ty.is(.@"enum") or ty.hasIncompleteSize()) break :unnamed;
2417 if (ty.isAnonymousRecord(p.comp)) {
2418 // An anonymous record appears as indirect fields on the parent
2419 try p.record_buf.append(.{
2420 .name = try p.getAnonymousName(first_tok),
2421 .ty = ty,
2422 });
2423 const node = try p.addNode(.{
2424 .tag = .indirect_record_field_decl,
2425 .ty = ty,
2426 .data = undefined,
2427 .loc = @enumFromInt(first_tok),
2428 });
2429 try p.decl_buf.append(node);
2430 try p.record.addFieldsFromAnonymous(p, ty);
2431 break; // must be followed by a semicolon
2432 }
2433 try p.err(.missing_declaration);
2434 } else {
2435 const interned_name = if (name_tok != 0) try StrInt.intern(p.comp, p.tokSlice(name_tok)) else try p.getAnonymousName(first_tok);
2436 try p.record_buf.append(.{
2437 .name = interned_name,
2438 .ty = ty,
2439 .name_tok = name_tok,
2440 .bit_width = bits,
2441 });
2442 if (name_tok != 0) try p.record.addField(p, interned_name, name_tok);
2443 const node = try p.addNode(.{
2444 .tag = .record_field_decl,
2445 .ty = ty,
2446 .data = .{ .decl = .{ .name = name_tok, .node = bits_node } },
2447 .loc = @enumFromInt(if (name_tok != 0) name_tok else first_tok),
2448 });
2449 try p.decl_buf.append(node);
2450 }
2451
2452 if (ty.isFunc()) {
2453 try p.errTok(.func_field, first_tok);
2454 } else if (ty.is(.variable_len_array)) {
2455 try p.errTok(.vla_field, first_tok);
2456 } else if (ty.is(.incomplete_array)) {
2457 if (p.record.kind == .keyword_union) {
2458 try p.errTok(.flexible_in_union, first_tok);
2459 }
2460 if (p.record.flexible_field) |some| {
2461 if (p.record.kind == .keyword_struct) {
2462 try p.errTok(.flexible_non_final, some);
2463 }
2464 }
2465 p.record.flexible_field = first_tok;
2466 } else if (ty.specifier != .invalid and ty.hasIncompleteSize()) {
2467 try p.errStr(.field_incomplete_ty, first_tok, try p.typeStr(ty));
2468 } else if (p.record.flexible_field) |some| {
2469 if (some != first_tok and p.record.kind == .keyword_struct) try p.errTok(.flexible_non_final, some);
2470 }
2471 if (p.eatToken(.comma) == null) break;
2472 }
2473
2474 if (p.eatToken(.semicolon) == null) {
2475 const tok_id = p.tok_ids[p.tok_i];
2476 if (tok_id == .r_brace) {
2477 try p.err(.missing_semicolon);
2478 } else {
2479 return p.errExpectedToken(.semicolon, tok_id);
2480 }
2481 }
2482
2483 return true;
2484}
2485
2486/// specQual : (typeSpec | typeQual | alignSpec)+
2487fn specQual(p: *Parser) Error!?Type {
2488 var spec: Type.Builder = .{};
2489 if (try p.typeSpec(&spec)) {
2490 return try spec.finish(p);
2491 }
2492 return null;
2493}
2494
2495/// enumSpec
2496/// : keyword_enum IDENTIFIER? (: typeName)? { enumerator (',' enumerator)? ',') }
2497/// | keyword_enum IDENTIFIER (: typeName)?
2498fn enumSpec(p: *Parser) Error!Type {
2499 const enum_tok = p.tok_i;
2500 p.tok_i += 1;
2501 const attr_buf_top = p.attr_buf.len;
2502 defer p.attr_buf.len = attr_buf_top;
2503 try p.attributeSpecifier();
2504
2505 const maybe_ident = try p.eatIdentifier();
2506 const fixed_ty = if (p.eatToken(.colon)) |colon| fixed: {
2507 const ty_start = p.tok_i;
2508 const fixed = (try p.specQual()) orelse {
2509 if (p.record.kind != .invalid) {
2510 // This is a bit field.
2511 p.tok_i -= 1;
2512 break :fixed null;
2513 }
2514 try p.err(.expected_type);
2515 try p.errTok(.enum_fixed, colon);
2516 break :fixed null;
2517 };
2518
2519 if (!fixed.isInt() or fixed.is(.@"enum")) {
2520 try p.errStr(.invalid_type_underlying_enum, ty_start, try p.typeStr(fixed));
2521 break :fixed Type.int;
2522 }
2523
2524 try p.errTok(.enum_fixed, colon);
2525 break :fixed fixed;
2526 } else null;
2527
2528 const l_brace = p.eatToken(.l_brace) orelse {
2529 const ident = maybe_ident orelse {
2530 try p.err(.ident_or_l_brace);
2531 return error.ParsingFailed;
2532 };
2533 // check if this is a reference to a previous type
2534 const interned_name = try StrInt.intern(p.comp, p.tokSlice(ident));
2535 if (try p.syms.findTag(p, interned_name, .keyword_enum, ident, p.tok_ids[p.tok_i])) |prev| {
2536 // only check fixed underlying type in forward declarations and not in references.
2537 if (p.tok_ids[p.tok_i] == .semicolon)
2538 try p.checkEnumFixedTy(fixed_ty, ident, prev);
2539 return prev.ty;
2540 } else {
2541 // this is a forward declaration, create a new enum Type.
2542 const enum_ty = try Type.Enum.create(p.arena, interned_name, fixed_ty);
2543 const ty = try Attribute.applyTypeAttributes(p, .{
2544 .specifier = .@"enum",
2545 .data = .{ .@"enum" = enum_ty },
2546 }, attr_buf_top, null);
2547 try p.syms.define(p.gpa, .{
2548 .kind = .@"enum",
2549 .name = interned_name,
2550 .tok = ident,
2551 .ty = ty,
2552 .val = .{},
2553 });
2554 try p.decl_buf.append(try p.addNode(.{
2555 .tag = .enum_forward_decl,
2556 .ty = ty,
2557 .data = .{ .decl_ref = ident },
2558 .loc = @enumFromInt(ident),
2559 }));
2560 return ty;
2561 }
2562 };
2563
2564 var done = false;
2565 errdefer if (!done) p.skipTo(.r_brace);
2566
2567 // Get forward declared type or create a new one
2568 var defined = false;
2569 const enum_ty: *Type.Enum = if (maybe_ident) |ident| enum_ty: {
2570 const ident_str = p.tokSlice(ident);
2571 const interned_name = try StrInt.intern(p.comp, ident_str);
2572 if (try p.syms.defineTag(p, interned_name, .keyword_enum, ident)) |prev| {
2573 const enum_ty = prev.ty.get(.@"enum").?.data.@"enum";
2574 if (!enum_ty.isIncomplete() and !enum_ty.fixed) {
2575 // if the enum isn't incomplete, this is a redefinition
2576 try p.errStr(.redefinition, ident, ident_str);
2577 try p.errTok(.previous_definition, prev.tok);
2578 } else {
2579 try p.checkEnumFixedTy(fixed_ty, ident, prev);
2580 defined = true;
2581 break :enum_ty enum_ty;
2582 }
2583 }
2584 break :enum_ty try Type.Enum.create(p.arena, interned_name, fixed_ty);
2585 } else try Type.Enum.create(p.arena, try p.getAnonymousName(enum_tok), fixed_ty);
2586
2587 // reserve space for this enum
2588 try p.decl_buf.append(.none);
2589 const decl_buf_top = p.decl_buf.items.len;
2590 const list_buf_top = p.list_buf.items.len;
2591 const enum_buf_top = p.enum_buf.items.len;
2592 errdefer p.decl_buf.items.len = decl_buf_top - 1;
2593 defer {
2594 p.decl_buf.items.len = decl_buf_top;
2595 p.list_buf.items.len = list_buf_top;
2596 p.enum_buf.items.len = enum_buf_top;
2597 }
2598
2599 var e = Enumerator.init(fixed_ty);
2600 while (try p.enumerator(&e)) |field_and_node| {
2601 try p.enum_buf.append(field_and_node.field);
2602 try p.list_buf.append(field_and_node.node);
2603 if (p.eatToken(.comma) == null) break;
2604 }
2605
2606 if (p.enum_buf.items.len == enum_buf_top) try p.err(.empty_enum);
2607 try p.expectClosing(l_brace, .r_brace);
2608 done = true;
2609 try p.attributeSpecifier();
2610
2611 const ty = try Attribute.applyTypeAttributes(p, .{
2612 .specifier = .@"enum",
2613 .data = .{ .@"enum" = enum_ty },
2614 }, attr_buf_top, null);
2615 if (!enum_ty.fixed) {
2616 const tag_specifier = try e.getTypeSpecifier(p, ty.enumIsPacked(p.comp), maybe_ident orelse enum_tok);
2617 enum_ty.tag_ty = .{ .specifier = tag_specifier };
2618 }
2619
2620 const enum_fields = p.enum_buf.items[enum_buf_top..];
2621 const field_nodes = p.list_buf.items[list_buf_top..];
2622
2623 if (fixed_ty == null) {
2624 for (enum_fields, 0..) |*field, i| {
2625 if (field.ty.eql(Type.int, p.comp, false)) continue;
2626
2627 const sym = p.syms.get(field.name, .vars) orelse continue;
2628 if (sym.kind != .enumeration) continue; // already an error
2629
2630 var res = Result{ .node = field.node, .ty = field.ty, .val = sym.val };
2631 const dest_ty = if (p.comp.fixedEnumTagSpecifier()) |some|
2632 Type{ .specifier = some }
2633 else if (try res.intFitsInType(p, Type.int))
2634 Type.int
2635 else if (!res.ty.eql(enum_ty.tag_ty, p.comp, false))
2636 enum_ty.tag_ty
2637 else
2638 continue;
2639
2640 const symbol = p.syms.getPtr(field.name, .vars);
2641 _ = try symbol.val.intCast(dest_ty, p.comp);
2642 symbol.ty = dest_ty;
2643 p.nodes.items(.ty)[@intFromEnum(field_nodes[i])] = dest_ty;
2644 field.ty = dest_ty;
2645 res.ty = dest_ty;
2646
2647 if (res.node != .none) {
2648 try res.implicitCast(p, .int_cast);
2649 field.node = res.node;
2650 p.nodes.items(.data)[@intFromEnum(field_nodes[i])].decl.node = res.node;
2651 }
2652 }
2653 }
2654
2655 enum_ty.fields = try p.arena.dupe(Type.Enum.Field, enum_fields);
2656
2657 // declare a symbol for the type
2658 if (maybe_ident != null and !defined) {
2659 try p.syms.define(p.gpa, .{
2660 .kind = .@"enum",
2661 .name = enum_ty.name,
2662 .ty = ty,
2663 .tok = maybe_ident.?,
2664 .val = .{},
2665 });
2666 }
2667
2668 // finish by creating a node
2669 var node: Tree.Node = .{
2670 .tag = .enum_decl_two,
2671 .ty = ty,
2672 .data = .{
2673 .two = .{ .none, .none },
2674 },
2675 .loc = @enumFromInt(maybe_ident orelse enum_tok),
2676 };
2677 switch (field_nodes.len) {
2678 0 => {},
2679 1 => node.data = .{ .two = .{ field_nodes[0], .none } },
2680 2 => node.data = .{ .two = .{ field_nodes[0], field_nodes[1] } },
2681 else => {
2682 node.tag = .enum_decl;
2683 node.data = .{ .range = try p.addList(field_nodes) };
2684 },
2685 }
2686 p.decl_buf.items[decl_buf_top - 1] = try p.addNode(node);
2687 if (p.func.ty == null) {
2688 _ = p.tentative_defs.remove(enum_ty.name);
2689 }
2690 return ty;
2691}
2692
2693fn checkEnumFixedTy(p: *Parser, fixed_ty: ?Type, ident_tok: TokenIndex, prev: Symbol) !void {
2694 const enum_ty = prev.ty.get(.@"enum").?.data.@"enum";
2695 if (fixed_ty) |some| {
2696 if (!enum_ty.fixed) {
2697 try p.errTok(.enum_prev_nonfixed, ident_tok);
2698 try p.errTok(.previous_definition, prev.tok);
2699 return error.ParsingFailed;
2700 }
2701
2702 if (!enum_ty.tag_ty.eql(some, p.comp, false)) {
2703 const str = try p.typePairStrExtra(some, " (was ", enum_ty.tag_ty);
2704 try p.errStr(.enum_different_explicit_ty, ident_tok, str);
2705 try p.errTok(.previous_definition, prev.tok);
2706 return error.ParsingFailed;
2707 }
2708 } else if (enum_ty.fixed) {
2709 try p.errTok(.enum_prev_fixed, ident_tok);
2710 try p.errTok(.previous_definition, prev.tok);
2711 return error.ParsingFailed;
2712 }
2713}
2714
2715const Enumerator = struct {
2716 res: Result,
2717 num_positive_bits: usize = 0,
2718 num_negative_bits: usize = 0,
2719 fixed: bool,
2720
2721 fn init(fixed_ty: ?Type) Enumerator {
2722 return .{
2723 .res = .{ .ty = fixed_ty orelse .{ .specifier = .int } },
2724 .fixed = fixed_ty != null,
2725 };
2726 }
2727
2728 /// Increment enumerator value adjusting type if needed.
2729 fn incr(e: *Enumerator, p: *Parser, tok: TokenIndex) !void {
2730 e.res.node = .none;
2731 const old_val = e.res.val;
2732 if (old_val.opt_ref == .none) {
2733 // First enumerator, set to 0 fits in all types.
2734 e.res.val = Value.zero;
2735 return;
2736 }
2737 if (try e.res.val.add(e.res.val, Value.one, e.res.ty, p.comp)) {
2738 if (e.fixed) {
2739 try p.errStr(.enum_not_representable_fixed, tok, try p.typeStr(e.res.ty));
2740 return;
2741 }
2742 const new_ty = if (p.comp.nextLargestIntSameSign(e.res.ty)) |larger| blk: {
2743 try p.errTok(.enumerator_overflow, tok);
2744 break :blk larger;
2745 } else blk: {
2746 const signed = !e.res.ty.isUnsignedInt(p.comp);
2747 const bit_size: u8 = @intCast(e.res.ty.bitSizeof(p.comp).? - @intFromBool(signed));
2748 try p.errExtra(.enum_not_representable, tok, .{ .pow_2_as_string = bit_size });
2749 break :blk Type{ .specifier = .ulong_long };
2750 };
2751 e.res.ty = new_ty;
2752 _ = try e.res.val.add(old_val, Value.one, e.res.ty, p.comp);
2753 }
2754 }
2755
2756 /// Set enumerator value to specified value.
2757 fn set(e: *Enumerator, p: *Parser, res: Result, tok: TokenIndex) !void {
2758 if (res.ty.specifier == .invalid) return;
2759 if (e.fixed and !res.ty.eql(e.res.ty, p.comp, false)) {
2760 if (!try res.intFitsInType(p, e.res.ty)) {
2761 try p.errStr(.enum_not_representable_fixed, tok, try p.typeStr(e.res.ty));
2762 return error.ParsingFailed;
2763 }
2764 var copy = res;
2765 copy.ty = e.res.ty;
2766 try copy.implicitCast(p, .int_cast);
2767 e.res = copy;
2768 } else {
2769 e.res = res;
2770 try e.res.intCast(p, e.res.ty.integerPromotion(p.comp), tok);
2771 }
2772 }
2773
2774 fn getTypeSpecifier(e: *const Enumerator, p: *Parser, is_packed: bool, tok: TokenIndex) !Type.Specifier {
2775 if (p.comp.fixedEnumTagSpecifier()) |tag_specifier| return tag_specifier;
2776
2777 const char_width = (Type{ .specifier = .schar }).sizeof(p.comp).? * 8;
2778 const short_width = (Type{ .specifier = .short }).sizeof(p.comp).? * 8;
2779 const int_width = (Type{ .specifier = .int }).sizeof(p.comp).? * 8;
2780 if (e.num_negative_bits > 0) {
2781 if (is_packed and e.num_negative_bits <= char_width and e.num_positive_bits < char_width) {
2782 return .schar;
2783 } else if (is_packed and e.num_negative_bits <= short_width and e.num_positive_bits < short_width) {
2784 return .short;
2785 } else if (e.num_negative_bits <= int_width and e.num_positive_bits < int_width) {
2786 return .int;
2787 }
2788 const long_width = (Type{ .specifier = .long }).sizeof(p.comp).? * 8;
2789 if (e.num_negative_bits <= long_width and e.num_positive_bits < long_width) {
2790 return .long;
2791 }
2792 const long_long_width = (Type{ .specifier = .long_long }).sizeof(p.comp).? * 8;
2793 if (e.num_negative_bits > long_long_width or e.num_positive_bits >= long_long_width) {
2794 try p.errTok(.enum_too_large, tok);
2795 }
2796 return .long_long;
2797 }
2798 if (is_packed and e.num_positive_bits <= char_width) {
2799 return .uchar;
2800 } else if (is_packed and e.num_positive_bits <= short_width) {
2801 return .ushort;
2802 } else if (e.num_positive_bits <= int_width) {
2803 return .uint;
2804 } else if (e.num_positive_bits <= (Type{ .specifier = .long }).sizeof(p.comp).? * 8) {
2805 return .ulong;
2806 }
2807 return .ulong_long;
2808 }
2809};
2810
2811const EnumFieldAndNode = struct { field: Type.Enum.Field, node: NodeIndex };
2812
2813/// enumerator : IDENTIFIER ('=' integerConstExpr)
2814fn enumerator(p: *Parser, e: *Enumerator) Error!?EnumFieldAndNode {
2815 _ = try p.pragma();
2816 const name_tok = (try p.eatIdentifier()) orelse {
2817 if (p.tok_ids[p.tok_i] == .r_brace) return null;
2818 try p.err(.expected_identifier);
2819 p.skipTo(.r_brace);
2820 return error.ParsingFailed;
2821 };
2822 const attr_buf_top = p.attr_buf.len;
2823 defer p.attr_buf.len = attr_buf_top;
2824 try p.attributeSpecifier();
2825
2826 const err_start = p.comp.diagnostics.list.items.len;
2827 if (p.eatToken(.equal)) |_| {
2828 const specified = try p.integerConstExpr(.gnu_folding_extension);
2829 if (specified.val.opt_ref == .none) {
2830 try p.errTok(.enum_val_unavailable, name_tok + 2);
2831 try e.incr(p, name_tok);
2832 } else {
2833 try e.set(p, specified, name_tok);
2834 }
2835 } else {
2836 try e.incr(p, name_tok);
2837 }
2838
2839 var res = e.res;
2840 res.ty = try Attribute.applyEnumeratorAttributes(p, res.ty, attr_buf_top);
2841
2842 if (res.ty.isUnsignedInt(p.comp) or res.val.compare(.gte, Value.zero, p.comp)) {
2843 e.num_positive_bits = @max(e.num_positive_bits, res.val.minUnsignedBits(p.comp));
2844 } else {
2845 e.num_negative_bits = @max(e.num_negative_bits, res.val.minSignedBits(p.comp));
2846 }
2847
2848 if (err_start == p.comp.diagnostics.list.items.len) {
2849 // only do these warnings if we didn't already warn about overflow or non-representable values
2850 if (e.res.val.compare(.lt, Value.zero, p.comp)) {
2851 const min_val = try Value.minInt(Type.int, p.comp);
2852 if (e.res.val.compare(.lt, min_val, p.comp)) {
2853 try p.errStr(.enumerator_too_small, name_tok, try e.res.str(p));
2854 }
2855 } else {
2856 const max_val = try Value.maxInt(Type.int, p.comp);
2857 if (e.res.val.compare(.gt, max_val, p.comp)) {
2858 try p.errStr(.enumerator_too_large, name_tok, try e.res.str(p));
2859 }
2860 }
2861 }
2862
2863 const interned_name = try StrInt.intern(p.comp, p.tokSlice(name_tok));
2864 try p.syms.defineEnumeration(p, interned_name, res.ty, name_tok, e.res.val);
2865 const node = try p.addNode(.{
2866 .tag = .enum_field_decl,
2867 .ty = res.ty,
2868 .data = .{ .decl = .{
2869 .name = name_tok,
2870 .node = res.node,
2871 } },
2872 .loc = @enumFromInt(name_tok),
2873 });
2874 try p.value_map.put(node, e.res.val);
2875 return EnumFieldAndNode{ .field = .{
2876 .name = interned_name,
2877 .ty = res.ty,
2878 .name_tok = name_tok,
2879 .node = res.node,
2880 }, .node = node };
2881}
2882
2883/// typeQual : keyword_const | keyword_restrict | keyword_volatile | keyword_atomic
2884fn typeQual(p: *Parser, b: *Type.Qualifiers.Builder) Error!bool {
2885 var any = false;
2886 while (true) {
2887 switch (p.tok_ids[p.tok_i]) {
2888 .keyword_restrict, .keyword_restrict1, .keyword_restrict2 => {
2889 if (b.restrict != null)
2890 try p.errStr(.duplicate_decl_spec, p.tok_i, "restrict")
2891 else
2892 b.restrict = p.tok_i;
2893 },
2894 .keyword_const, .keyword_const1, .keyword_const2 => {
2895 if (b.@"const" != null)
2896 try p.errStr(.duplicate_decl_spec, p.tok_i, "const")
2897 else
2898 b.@"const" = p.tok_i;
2899 },
2900 .keyword_volatile, .keyword_volatile1, .keyword_volatile2 => {
2901 if (b.@"volatile" != null)
2902 try p.errStr(.duplicate_decl_spec, p.tok_i, "volatile")
2903 else
2904 b.@"volatile" = p.tok_i;
2905 },
2906 .keyword_atomic => {
2907 // _Atomic(typeName) instead of just _Atomic
2908 if (p.tok_ids[p.tok_i + 1] == .l_paren) break;
2909 if (b.atomic != null)
2910 try p.errStr(.duplicate_decl_spec, p.tok_i, "atomic")
2911 else
2912 b.atomic = p.tok_i;
2913 },
2914 else => break,
2915 }
2916 p.tok_i += 1;
2917 any = true;
2918 }
2919 return any;
2920}
2921
2922const Declarator = struct {
2923 name: TokenIndex,
2924 ty: Type,
2925 func_declarator: ?TokenIndex = null,
2926 old_style_func: ?TokenIndex = null,
2927};
2928const DeclaratorKind = enum { normal, abstract, param, record };
2929
2930/// declarator : pointer? (IDENTIFIER | '(' declarator ')') directDeclarator*
2931/// abstractDeclarator
2932/// : pointer? ('(' abstractDeclarator ')')? directAbstractDeclarator*
2933fn declarator(
2934 p: *Parser,
2935 base_type: Type,
2936 kind: DeclaratorKind,
2937) Error!?Declarator {
2938 const start = p.tok_i;
2939 var d = Declarator{ .name = 0, .ty = try p.pointer(base_type) };
2940 if (base_type.is(.auto_type) and !d.ty.is(.auto_type)) {
2941 try p.errTok(.auto_type_requires_plain_declarator, start);
2942 return error.ParsingFailed;
2943 }
2944
2945 const maybe_ident = p.tok_i;
2946 if (kind != .abstract and (try p.eatIdentifier()) != null) {
2947 d.name = maybe_ident;
2948 const combine_tok = p.tok_i;
2949 d.ty = try p.directDeclarator(d.ty, &d, kind);
2950 try d.ty.validateCombinedType(p, combine_tok);
2951 return d;
2952 } else if (p.eatToken(.l_paren)) |l_paren| blk: {
2953 var res = (try p.declarator(.{ .specifier = .void }, kind)) orelse {
2954 p.tok_i = l_paren;
2955 break :blk;
2956 };
2957 try p.expectClosing(l_paren, .r_paren);
2958 const suffix_start = p.tok_i;
2959 const outer = try p.directDeclarator(d.ty, &d, kind);
2960 try res.ty.combine(outer);
2961 try res.ty.validateCombinedType(p, suffix_start);
2962 res.old_style_func = d.old_style_func;
2963 if (d.func_declarator) |some| res.func_declarator = some;
2964 return res;
2965 }
2966
2967 const expected_ident = p.tok_i;
2968
2969 d.ty = try p.directDeclarator(d.ty, &d, kind);
2970
2971 if (kind == .normal and !d.ty.isEnumOrRecord()) {
2972 try p.errTok(.expected_ident_or_l_paren, expected_ident);
2973 return error.ParsingFailed;
2974 }
2975 try d.ty.validateCombinedType(p, expected_ident);
2976 if (start == p.tok_i) return null;
2977 return d;
2978}
2979
2980/// directDeclarator
2981/// : '[' typeQual* assignExpr? ']' directDeclarator?
2982/// | '[' keyword_static typeQual* assignExpr ']' directDeclarator?
2983/// | '[' typeQual+ keyword_static assignExpr ']' directDeclarator?
2984/// | '[' typeQual* '*' ']' directDeclarator?
2985/// | '(' paramDecls ')' directDeclarator?
2986/// | '(' (IDENTIFIER (',' IDENTIFIER))? ')' directDeclarator?
2987/// directAbstractDeclarator
2988/// : '[' typeQual* assignExpr? ']'
2989/// | '[' keyword_static typeQual* assignExpr ']'
2990/// | '[' typeQual+ keyword_static assignExpr ']'
2991/// | '[' '*' ']'
2992/// | '(' paramDecls? ')'
2993fn directDeclarator(p: *Parser, base_type: Type, d: *Declarator, kind: DeclaratorKind) Error!Type {
2994 if (p.eatToken(.l_bracket)) |l_bracket| {
2995 if (p.tok_ids[p.tok_i] == .l_bracket) {
2996 switch (kind) {
2997 .normal, .record => if (p.comp.langopts.standard.atLeast(.c23)) {
2998 p.tok_i -= 1;
2999 return base_type;
3000 },
3001 .param, .abstract => {},
3002 }
3003 try p.err(.expected_expr);
3004 return error.ParsingFailed;
3005 }
3006 var res_ty = Type{
3007 // so that we can get any restrict type that might be present
3008 .specifier = .pointer,
3009 };
3010 var quals = Type.Qualifiers.Builder{};
3011
3012 var got_quals = try p.typeQual(&quals);
3013 var static = p.eatToken(.keyword_static);
3014 if (static != null and !got_quals) got_quals = try p.typeQual(&quals);
3015 var star = p.eatToken(.asterisk);
3016 const size_tok = p.tok_i;
3017
3018 const const_decl_folding = p.const_decl_folding;
3019 p.const_decl_folding = .gnu_vla_folding_extension;
3020 const size = if (star) |_| Result{} else try p.assignExpr();
3021 p.const_decl_folding = const_decl_folding;
3022
3023 try p.expectClosing(l_bracket, .r_bracket);
3024
3025 if (star != null and static != null) {
3026 try p.errTok(.invalid_static_star, static.?);
3027 static = null;
3028 }
3029 if (kind != .param) {
3030 if (static != null)
3031 try p.errTok(.static_non_param, l_bracket)
3032 else if (got_quals)
3033 try p.errTok(.array_qualifiers, l_bracket);
3034 if (star) |some| try p.errTok(.star_non_param, some);
3035 static = null;
3036 quals = .{};
3037 star = null;
3038 } else {
3039 try quals.finish(p, &res_ty);
3040 }
3041 if (static) |_| try size.expect(p);
3042
3043 if (base_type.is(.auto_type)) {
3044 try p.errStr(.array_of_auto_type, d.name, p.tokSlice(d.name));
3045 return error.ParsingFailed;
3046 }
3047
3048 const outer = try p.directDeclarator(base_type, d, kind);
3049
3050 if (!size.ty.isInt()) {
3051 try p.errStr(.array_size_non_int, size_tok, try p.typeStr(size.ty));
3052 return error.ParsingFailed;
3053 }
3054 if (base_type.is(.c23_auto) or outer.is(.invalid)) {
3055 // issue error later
3056 return Type.invalid;
3057 } else if (size.val.opt_ref == .none) {
3058 if (size.node != .none) {
3059 try p.errTok(.vla, size_tok);
3060 if (p.func.ty == null and kind != .param and p.record.kind == .invalid) {
3061 try p.errTok(.variable_len_array_file_scope, d.name);
3062 }
3063 const expr_ty = try p.arena.create(Type.Expr);
3064 expr_ty.ty = .{ .specifier = .void };
3065 expr_ty.node = size.node;
3066 res_ty.data = .{ .expr = expr_ty };
3067 res_ty.specifier = .variable_len_array;
3068
3069 if (static) |some| try p.errTok(.useless_static, some);
3070 } else if (star) |_| {
3071 const elem_ty = try p.arena.create(Type);
3072 elem_ty.* = .{ .specifier = .void };
3073 res_ty.data = .{ .sub_type = elem_ty };
3074 res_ty.specifier = .unspecified_variable_len_array;
3075 } else {
3076 const arr_ty = try p.arena.create(Type.Array);
3077 arr_ty.elem = .{ .specifier = .void };
3078 arr_ty.len = 0;
3079 res_ty.data = .{ .array = arr_ty };
3080 res_ty.specifier = .incomplete_array;
3081 }
3082 } else {
3083 // `outer` is validated later so it may be invalid here
3084 const outer_size = outer.sizeof(p.comp);
3085 const max_elems = p.comp.maxArrayBytes() / @max(1, outer_size orelse 1);
3086
3087 var size_val = size.val;
3088 if (size_val.isZero(p.comp)) {
3089 try p.errTok(.zero_length_array, l_bracket);
3090 } else if (size_val.compare(.lt, Value.zero, p.comp)) {
3091 try p.errTok(.negative_array_size, l_bracket);
3092 return error.ParsingFailed;
3093 }
3094 const arr_ty = try p.arena.create(Type.Array);
3095 arr_ty.elem = .{ .specifier = .void };
3096 arr_ty.len = size_val.toInt(u64, p.comp) orelse std.math.maxInt(u64);
3097 if (arr_ty.len > max_elems) {
3098 try p.errTok(.array_too_large, l_bracket);
3099 arr_ty.len = max_elems;
3100 }
3101 res_ty.data = .{ .array = arr_ty };
3102 res_ty.specifier = if (static != null) .static_array else .array;
3103 }
3104
3105 try res_ty.combine(outer);
3106 return res_ty;
3107 } else if (p.eatToken(.l_paren)) |l_paren| {
3108 d.func_declarator = l_paren;
3109
3110 const func_ty = try p.arena.create(Type.Func);
3111 func_ty.params = &.{};
3112 func_ty.return_type.specifier = .void;
3113 var specifier: Type.Specifier = .func;
3114
3115 if (p.eatToken(.ellipsis)) |_| {
3116 try p.err(.param_before_var_args);
3117 try p.expectClosing(l_paren, .r_paren);
3118 var res_ty = Type{ .specifier = .func, .data = .{ .func = func_ty } };
3119
3120 const outer = try p.directDeclarator(base_type, d, kind);
3121 try res_ty.combine(outer);
3122 return res_ty;
3123 }
3124
3125 if (try p.paramDecls(d)) |params| {
3126 func_ty.params = params;
3127 if (p.eatToken(.ellipsis)) |_| specifier = .var_args_func;
3128 } else if (p.tok_ids[p.tok_i] == .r_paren) {
3129 specifier = if (p.comp.langopts.standard.atLeast(.c23))
3130 .func
3131 else
3132 .old_style_func;
3133 } else if (p.tok_ids[p.tok_i] == .identifier or p.tok_ids[p.tok_i] == .extended_identifier) {
3134 d.old_style_func = p.tok_i;
3135 const param_buf_top = p.param_buf.items.len;
3136 try p.syms.pushScope(p);
3137 defer {
3138 p.param_buf.items.len = param_buf_top;
3139 p.syms.popScope();
3140 }
3141
3142 specifier = .old_style_func;
3143 while (true) {
3144 const name_tok = try p.expectIdentifier();
3145 const interned_name = try StrInt.intern(p.comp, p.tokSlice(name_tok));
3146 try p.syms.defineParam(p, interned_name, undefined, name_tok);
3147 try p.param_buf.append(.{
3148 .name = interned_name,
3149 .name_tok = name_tok,
3150 .ty = .{ .specifier = .int },
3151 });
3152 if (p.eatToken(.comma) == null) break;
3153 }
3154 func_ty.params = try p.arena.dupe(Type.Func.Param, p.param_buf.items[param_buf_top..]);
3155 } else {
3156 try p.err(.expected_param_decl);
3157 }
3158
3159 try p.expectClosing(l_paren, .r_paren);
3160 var res_ty = Type{
3161 .specifier = specifier,
3162 .data = .{ .func = func_ty },
3163 };
3164
3165 const outer = try p.directDeclarator(base_type, d, kind);
3166 try res_ty.combine(outer);
3167 return res_ty;
3168 } else return base_type;
3169}
3170
3171/// pointer : '*' typeQual* pointer?
3172fn pointer(p: *Parser, base_ty: Type) Error!Type {
3173 var ty = base_ty;
3174 while (p.eatToken(.asterisk)) |_| {
3175 if (!ty.is(.invalid)) {
3176 const elem_ty = try p.arena.create(Type);
3177 elem_ty.* = ty;
3178 ty = Type{
3179 .specifier = .pointer,
3180 .data = .{ .sub_type = elem_ty },
3181 };
3182 }
3183 var quals = Type.Qualifiers.Builder{};
3184 _ = try p.typeQual(&quals);
3185 try quals.finish(p, &ty);
3186 }
3187 return ty;
3188}
3189
3190/// paramDecls : paramDecl (',' paramDecl)* (',' '...')
3191/// paramDecl : declSpec (declarator | abstractDeclarator)
3192fn paramDecls(p: *Parser, d: *Declarator) Error!?[]Type.Func.Param {
3193 // TODO warn about visibility of types declared here
3194 const param_buf_top = p.param_buf.items.len;
3195 defer p.param_buf.items.len = param_buf_top;
3196 try p.syms.pushScope(p);
3197 defer p.syms.popScope();
3198
3199 while (true) {
3200 const attr_buf_top = p.attr_buf.len;
3201 defer p.attr_buf.len = attr_buf_top;
3202 const param_decl_spec = if (try p.declSpec()) |some|
3203 some
3204 else if (p.comp.langopts.standard.atLeast(.c23) and
3205 (p.tok_ids[p.tok_i] == .identifier or p.tok_ids[p.tok_i] == .extended_identifier))
3206 {
3207 // handle deprecated K&R style parameters
3208 const identifier = try p.expectIdentifier();
3209 try p.errStr(.unknown_type_name, identifier, p.tokSlice(identifier));
3210 if (d.old_style_func == null) d.old_style_func = identifier;
3211
3212 try p.param_buf.append(.{
3213 .name = try StrInt.intern(p.comp, p.tokSlice(identifier)),
3214 .name_tok = identifier,
3215 .ty = .{ .specifier = .int },
3216 });
3217
3218 if (p.eatToken(.comma) == null) break;
3219 if (p.tok_ids[p.tok_i] == .ellipsis) break;
3220 continue;
3221 } else if (p.param_buf.items.len == param_buf_top) {
3222 return null;
3223 } else blk: {
3224 var spec: Type.Builder = .{};
3225 break :blk DeclSpec{ .ty = try spec.finish(p) };
3226 };
3227
3228 var name_tok: TokenIndex = 0;
3229 const first_tok = p.tok_i;
3230 var param_ty = param_decl_spec.ty;
3231 if (try p.declarator(param_decl_spec.ty, .param)) |some| {
3232 if (some.old_style_func) |tok_i| try p.errTok(.invalid_old_style_params, tok_i);
3233 try p.attributeSpecifier();
3234
3235 name_tok = some.name;
3236 param_ty = some.ty;
3237 if (some.name != 0) {
3238 const interned_name = try StrInt.intern(p.comp, p.tokSlice(name_tok));
3239 try p.syms.defineParam(p, interned_name, param_ty, name_tok);
3240 }
3241 }
3242 param_ty = try Attribute.applyParameterAttributes(p, param_ty, attr_buf_top, .alignas_on_param);
3243
3244 if (param_ty.isFunc()) {
3245 // params declared as functions are converted to function pointers
3246 const elem_ty = try p.arena.create(Type);
3247 elem_ty.* = param_ty;
3248 param_ty = Type{
3249 .specifier = .pointer,
3250 .data = .{ .sub_type = elem_ty },
3251 };
3252 } else if (param_ty.isArray()) {
3253 // params declared as arrays are converted to pointers
3254 param_ty.decayArray();
3255 } else if (param_ty.is(.void)) {
3256 // validate void parameters
3257 if (p.param_buf.items.len == param_buf_top) {
3258 if (p.tok_ids[p.tok_i] != .r_paren) {
3259 try p.err(.void_only_param);
3260 if (param_ty.anyQual()) try p.err(.void_param_qualified);
3261 return error.ParsingFailed;
3262 }
3263 return &[0]Type.Func.Param{};
3264 }
3265 try p.err(.void_must_be_first_param);
3266 return error.ParsingFailed;
3267 }
3268
3269 try param_decl_spec.validateParam(p, &param_ty);
3270 try p.param_buf.append(.{
3271 .name = if (name_tok == 0) .empty else try StrInt.intern(p.comp, p.tokSlice(name_tok)),
3272 .name_tok = if (name_tok == 0) first_tok else name_tok,
3273 .ty = param_ty,
3274 });
3275
3276 if (p.eatToken(.comma) == null) break;
3277 if (p.tok_ids[p.tok_i] == .ellipsis) break;
3278 }
3279 return try p.arena.dupe(Type.Func.Param, p.param_buf.items[param_buf_top..]);
3280}
3281
3282/// typeName : specQual abstractDeclarator
3283fn typeName(p: *Parser) Error!?Type {
3284 const attr_buf_top = p.attr_buf.len;
3285 defer p.attr_buf.len = attr_buf_top;
3286 const ty = (try p.specQual()) orelse return null;
3287 if (try p.declarator(ty, .abstract)) |some| {
3288 if (some.old_style_func) |tok_i| try p.errTok(.invalid_old_style_params, tok_i);
3289 return try Attribute.applyTypeAttributes(p, some.ty, attr_buf_top, .align_ignored);
3290 }
3291 return try Attribute.applyTypeAttributes(p, ty, attr_buf_top, .align_ignored);
3292}
3293
3294fn complexInitializer(p: *Parser, init_ty: Type) Error!Result {
3295 assert(p.tok_ids[p.tok_i] == .l_brace);
3296 assert(init_ty.isComplex());
3297
3298 const real_ty = init_ty.makeReal();
3299 if (real_ty.isInt()) {
3300 return p.todo("Complex integer initializers");
3301 }
3302 const l_brace = p.tok_i;
3303 p.tok_i += 1;
3304 try p.errTok(.complex_component_init, l_brace);
3305
3306 const first_tok = p.tok_i;
3307 var first = try p.assignExpr();
3308 try first.expect(p);
3309 try p.coerceInit(&first, first_tok, real_ty);
3310
3311 var second: Result = .{
3312 .ty = real_ty,
3313 .val = Value.zero,
3314 };
3315 if (p.eatToken(.comma)) |_| {
3316 const second_tok = p.tok_i;
3317 const maybe_second = try p.assignExpr();
3318 if (!maybe_second.empty(p)) {
3319 second = maybe_second;
3320 try p.coerceInit(&second, second_tok, real_ty);
3321 }
3322 }
3323
3324 // Eat excess initializers
3325 var extra_tok: ?TokenIndex = null;
3326 while (p.eatToken(.comma)) |_| {
3327 if (p.tok_ids[p.tok_i] == .r_brace) break;
3328 extra_tok = p.tok_i;
3329 const extra = try p.assignExpr();
3330 if (extra.empty(p)) {
3331 try p.errTok(.expected_expr, p.tok_i);
3332 p.skipTo(.r_brace);
3333 return error.ParsingFailed;
3334 }
3335 }
3336 try p.expectClosing(l_brace, .r_brace);
3337 if (extra_tok) |tok| {
3338 try p.errTok(.excess_scalar_init, tok);
3339 }
3340
3341 const arr_init_node: Tree.Node = .{
3342 .tag = .array_init_expr_two,
3343 .ty = init_ty,
3344 .data = .{ .two = .{ first.node, second.node } },
3345 .loc = @enumFromInt(l_brace),
3346 };
3347 var res: Result = .{
3348 .node = try p.addNode(arr_init_node),
3349 .ty = init_ty,
3350 };
3351 if (first.val.opt_ref != .none and second.val.opt_ref != .none) {
3352 res.val = try Value.intern(p.comp, switch (real_ty.bitSizeof(p.comp).?) {
3353 32 => .{ .complex = .{ .cf32 = .{ first.val.toFloat(f32, p.comp), second.val.toFloat(f32, p.comp) } } },
3354 64 => .{ .complex = .{ .cf64 = .{ first.val.toFloat(f64, p.comp), second.val.toFloat(f64, p.comp) } } },
3355 80 => .{ .complex = .{ .cf80 = .{ first.val.toFloat(f80, p.comp), second.val.toFloat(f80, p.comp) } } },
3356 128 => .{ .complex = .{ .cf128 = .{ first.val.toFloat(f128, p.comp), second.val.toFloat(f128, p.comp) } } },
3357 else => unreachable,
3358 });
3359 }
3360 return res;
3361}
3362
3363/// initializer
3364/// : assignExpr
3365/// | '{' initializerItems '}'
3366fn initializer(p: *Parser, init_ty: Type) Error!Result {
3367 // fast path for non-braced initializers
3368 if (p.tok_ids[p.tok_i] != .l_brace) {
3369 const tok = p.tok_i;
3370 var res = try p.assignExpr();
3371 try res.expect(p);
3372 if (try p.coerceArrayInit(&res, tok, init_ty)) return res;
3373 try p.coerceInit(&res, tok, init_ty);
3374 return res;
3375 }
3376 if (init_ty.is(.auto_type)) {
3377 try p.err(.auto_type_with_init_list);
3378 return error.ParsingFailed;
3379 }
3380
3381 if (init_ty.isComplex()) {
3382 return p.complexInitializer(init_ty);
3383 }
3384 var il: InitList = .{};
3385 defer il.deinit(p.gpa);
3386
3387 _ = try p.initializerItem(&il, init_ty);
3388
3389 const res = try p.convertInitList(il, init_ty);
3390 var res_ty = p.nodes.items(.ty)[@intFromEnum(res)];
3391 res_ty.qual = init_ty.qual;
3392 return Result{ .ty = res_ty, .node = res };
3393}
3394
3395/// initializerItems : designation? initializer (',' designation? initializer)* ','?
3396/// designation : designator+ '='
3397/// designator
3398/// : '[' integerConstExpr ']'
3399/// | '.' identifier
3400fn initializerItem(p: *Parser, il: *InitList, init_ty: Type) Error!bool {
3401 const l_brace = p.eatToken(.l_brace) orelse {
3402 const tok = p.tok_i;
3403 var res = try p.assignExpr();
3404 if (res.empty(p)) return false;
3405
3406 const arr = try p.coerceArrayInit(&res, tok, init_ty);
3407 if (!arr) try p.coerceInit(&res, tok, init_ty);
3408 if (il.tok != 0) {
3409 try p.errTok(.initializer_overrides, tok);
3410 try p.errTok(.previous_initializer, il.tok);
3411 }
3412 il.node = res.node;
3413 il.tok = tok;
3414 return true;
3415 };
3416
3417 const is_scalar = init_ty.isScalar();
3418 const is_complex = init_ty.isComplex();
3419 const scalar_inits_needed: usize = if (is_complex) 2 else 1;
3420 if (p.eatToken(.r_brace)) |_| {
3421 if (is_scalar) try p.errTok(.empty_scalar_init, l_brace);
3422 if (il.tok != 0) {
3423 try p.errTok(.initializer_overrides, l_brace);
3424 try p.errTok(.previous_initializer, il.tok);
3425 }
3426 il.node = .none;
3427 il.tok = l_brace;
3428 return true;
3429 }
3430
3431 var count: u64 = 0;
3432 var warned_excess = false;
3433 var is_str_init = false;
3434 var index_hint: ?u64 = null;
3435 while (true) : (count += 1) {
3436 errdefer p.skipTo(.r_brace);
3437
3438 var first_tok = p.tok_i;
3439 var cur_ty = init_ty;
3440 var cur_il = il;
3441 var designation = false;
3442 var cur_index_hint: ?u64 = null;
3443 while (true) {
3444 if (p.eatToken(.l_bracket)) |l_bracket| {
3445 if (!cur_ty.isArray()) {
3446 try p.errStr(.invalid_array_designator, l_bracket, try p.typeStr(cur_ty));
3447 return error.ParsingFailed;
3448 }
3449 const expr_tok = p.tok_i;
3450 const index_res = try p.integerConstExpr(.gnu_folding_extension);
3451 try p.expectClosing(l_bracket, .r_bracket);
3452
3453 if (index_res.val.opt_ref == .none) {
3454 try p.errTok(.expected_integer_constant_expr, expr_tok);
3455 return error.ParsingFailed;
3456 } else if (index_res.val.compare(.lt, Value.zero, p.comp)) {
3457 try p.errStr(.negative_array_designator, l_bracket + 1, try index_res.str(p));
3458 return error.ParsingFailed;
3459 }
3460
3461 const max_len = cur_ty.arrayLen() orelse std.math.maxInt(usize);
3462 const index_int = index_res.val.toInt(u64, p.comp) orelse std.math.maxInt(u64);
3463 if (index_int >= max_len) {
3464 try p.errStr(.oob_array_designator, l_bracket + 1, try index_res.str(p));
3465 return error.ParsingFailed;
3466 }
3467 cur_index_hint = cur_index_hint orelse index_int;
3468
3469 cur_il = try cur_il.find(p.gpa, index_int);
3470 cur_ty = cur_ty.elemType();
3471 designation = true;
3472 } else if (p.eatToken(.period)) |period| {
3473 const field_tok = try p.expectIdentifier();
3474 const field_str = p.tokSlice(field_tok);
3475 const field_name = try StrInt.intern(p.comp, field_str);
3476 cur_ty = cur_ty.canonicalize(.standard);
3477 if (!cur_ty.isRecord()) {
3478 try p.errStr(.invalid_field_designator, period, try p.typeStr(cur_ty));
3479 return error.ParsingFailed;
3480 } else if (!cur_ty.hasField(field_name)) {
3481 try p.errStr(.no_such_field_designator, period, field_str);
3482 return error.ParsingFailed;
3483 }
3484
3485 // TODO check if union already has field set
3486 outer: while (true) {
3487 for (cur_ty.data.record.fields, 0..) |f, i| {
3488 if (f.isAnonymousRecord()) {
3489 // Recurse into anonymous field if it has a field by the name.
3490 if (!f.ty.hasField(field_name)) continue;
3491 cur_ty = f.ty.canonicalize(.standard);
3492 cur_il = try il.find(p.gpa, i);
3493 cur_index_hint = cur_index_hint orelse i;
3494 continue :outer;
3495 }
3496 if (field_name == f.name) {
3497 cur_il = try cur_il.find(p.gpa, i);
3498 cur_ty = f.ty;
3499 cur_index_hint = cur_index_hint orelse i;
3500 break :outer;
3501 }
3502 }
3503 unreachable; // we already checked that the starting type has this field
3504 }
3505 designation = true;
3506 } else break;
3507 }
3508 if (designation) index_hint = null;
3509 defer index_hint = cur_index_hint orelse null;
3510
3511 if (designation) _ = try p.expectToken(.equal);
3512
3513 if (!designation and cur_ty.hasAttribute(.designated_init)) {
3514 try p.err(.designated_init_needed);
3515 }
3516
3517 var saw = false;
3518 if (is_str_init and p.isStringInit(init_ty)) {
3519 // discard further strings
3520 var tmp_il = InitList{};
3521 defer tmp_il.deinit(p.gpa);
3522 saw = try p.initializerItem(&tmp_il, .{ .specifier = .void });
3523 } else if (count == 0 and p.isStringInit(init_ty)) {
3524 is_str_init = true;
3525 saw = try p.initializerItem(il, init_ty);
3526 } else if (is_scalar and count >= scalar_inits_needed) {
3527 // discard further scalars
3528 var tmp_il = InitList{};
3529 defer tmp_il.deinit(p.gpa);
3530 saw = try p.initializerItem(&tmp_il, .{ .specifier = .void });
3531 } else if (p.tok_ids[p.tok_i] == .l_brace) {
3532 if (designation) {
3533 // designation overrides previous value, let existing mechanism handle it
3534 saw = try p.initializerItem(cur_il, cur_ty);
3535 } else if (try p.findAggregateInitializer(&cur_il, &cur_ty, &index_hint)) {
3536 saw = try p.initializerItem(cur_il, cur_ty);
3537 } else {
3538 // discard further values
3539 var tmp_il = InitList{};
3540 defer tmp_il.deinit(p.gpa);
3541 saw = try p.initializerItem(&tmp_il, .{ .specifier = .void });
3542 if (!warned_excess) try p.errTok(if (init_ty.isArray()) .excess_array_init else .excess_struct_init, first_tok);
3543 warned_excess = true;
3544 }
3545 } else single_item: {
3546 first_tok = p.tok_i;
3547 var res = try p.assignExpr();
3548 saw = !res.empty(p);
3549 if (!saw) break :single_item;
3550
3551 excess: {
3552 if (index_hint) |*hint| {
3553 if (try p.findScalarInitializerAt(&cur_il, &cur_ty, &res, first_tok, hint)) break :excess;
3554 } else if (try p.findScalarInitializer(&cur_il, &cur_ty, &res, first_tok)) break :excess;
3555
3556 if (designation) break :excess;
3557 if (!warned_excess) try p.errTok(if (init_ty.isArray()) .excess_array_init else .excess_struct_init, first_tok);
3558 warned_excess = true;
3559
3560 break :single_item;
3561 }
3562
3563 const arr = try p.coerceArrayInit(&res, first_tok, cur_ty);
3564 if (!arr) try p.coerceInit(&res, first_tok, cur_ty);
3565 if (cur_il.tok != 0) {
3566 try p.errTok(.initializer_overrides, first_tok);
3567 try p.errTok(.previous_initializer, cur_il.tok);
3568 }
3569 cur_il.node = res.node;
3570 cur_il.tok = first_tok;
3571 }
3572
3573 if (!saw) {
3574 if (designation) {
3575 try p.err(.expected_expr);
3576 return error.ParsingFailed;
3577 }
3578 break;
3579 } else if (count == 1) {
3580 if (is_str_init) try p.errTok(.excess_str_init, first_tok);
3581 if (is_scalar and !is_complex) try p.errTok(.excess_scalar_init, first_tok);
3582 } else if (count == 2) {
3583 if (is_scalar and is_complex) try p.errTok(.excess_scalar_init, first_tok);
3584 }
3585
3586 if (p.eatToken(.comma) == null) break;
3587 }
3588 try p.expectClosing(l_brace, .r_brace);
3589
3590 if (is_complex and count == 1) { // count of 1 means we saw exactly 2 items in the initializer list
3591 try p.errTok(.complex_component_init, l_brace);
3592 }
3593 if (is_scalar or is_str_init) return true;
3594 if (il.tok != 0) {
3595 try p.errTok(.initializer_overrides, l_brace);
3596 try p.errTok(.previous_initializer, il.tok);
3597 }
3598 il.node = .none;
3599 il.tok = l_brace;
3600 return true;
3601}
3602
3603/// Returns true if the value is unused.
3604fn findScalarInitializerAt(p: *Parser, il: **InitList, ty: *Type, res: *Result, first_tok: TokenIndex, start_index: *u64) Error!bool {
3605 if (ty.isArray()) {
3606 if (il.*.node != .none) return false;
3607 start_index.* += 1;
3608
3609 const arr_ty = ty.*;
3610 const elem_count = arr_ty.arrayLen() orelse std.math.maxInt(u64);
3611 if (elem_count == 0) {
3612 try p.errTok(.empty_aggregate_init_braces, first_tok);
3613 return error.ParsingFailed;
3614 }
3615 const elem_ty = arr_ty.elemType();
3616 const arr_il = il.*;
3617 if (start_index.* < elem_count) {
3618 ty.* = elem_ty;
3619 il.* = try arr_il.find(p.gpa, start_index.*);
3620 _ = try p.findScalarInitializer(il, ty, res, first_tok);
3621 return true;
3622 }
3623 return false;
3624 } else if (ty.get(.@"struct")) |struct_ty| {
3625 if (il.*.node != .none) return false;
3626 start_index.* += 1;
3627
3628 const fields = struct_ty.data.record.fields;
3629 if (fields.len == 0) {
3630 try p.errTok(.empty_aggregate_init_braces, first_tok);
3631 return error.ParsingFailed;
3632 }
3633 const struct_il = il.*;
3634 if (start_index.* < fields.len) {
3635 const field = fields[@intCast(start_index.*)];
3636 ty.* = field.ty;
3637 il.* = try struct_il.find(p.gpa, start_index.*);
3638 _ = try p.findScalarInitializer(il, ty, res, first_tok);
3639 return true;
3640 }
3641 return false;
3642 } else if (ty.get(.@"union")) |_| {
3643 return false;
3644 }
3645 return il.*.node == .none;
3646}
3647
3648/// Returns true if the value is unused.
3649fn findScalarInitializer(p: *Parser, il: **InitList, ty: *Type, res: *Result, first_tok: TokenIndex) Error!bool {
3650 const actual_ty = res.ty;
3651 if (ty.isArray() or ty.isComplex()) {
3652 if (il.*.node != .none) return false;
3653 if (try p.coerceArrayInitExtra(res, first_tok, ty.*, false)) return true;
3654 const start_index = il.*.list.items.len;
3655 var index = if (start_index != 0) il.*.list.items[start_index - 1].index else start_index;
3656
3657 const arr_ty = ty.*;
3658 const elem_count: u64 = arr_ty.expectedInitListSize() orelse std.math.maxInt(u64);
3659 if (elem_count == 0) {
3660 try p.errTok(.empty_aggregate_init_braces, first_tok);
3661 return error.ParsingFailed;
3662 }
3663 const elem_ty = arr_ty.elemType();
3664 const arr_il = il.*;
3665 while (index < elem_count) : (index += 1) {
3666 ty.* = elem_ty;
3667 il.* = try arr_il.find(p.gpa, index);
3668 if (il.*.node == .none and actual_ty.eql(elem_ty, p.comp, false)) return true;
3669 if (try p.findScalarInitializer(il, ty, res, first_tok)) return true;
3670 }
3671 return false;
3672 } else if (ty.get(.@"struct")) |struct_ty| {
3673 if (il.*.node != .none) return false;
3674 if (actual_ty.eql(ty.*, p.comp, false)) return true;
3675 const start_index = il.*.list.items.len;
3676 var index = if (start_index != 0) il.*.list.items[start_index - 1].index + 1 else start_index;
3677
3678 const fields = struct_ty.data.record.fields;
3679 if (fields.len == 0) {
3680 try p.errTok(.empty_aggregate_init_braces, first_tok);
3681 return error.ParsingFailed;
3682 }
3683 const struct_il = il.*;
3684 while (index < fields.len) : (index += 1) {
3685 const field = fields[@intCast(index)];
3686 ty.* = field.ty;
3687 il.* = try struct_il.find(p.gpa, index);
3688 if (il.*.node == .none and actual_ty.eql(field.ty, p.comp, false)) return true;
3689 if (il.*.node == .none and try p.coerceArrayInitExtra(res, first_tok, ty.*, false)) return true;
3690 if (try p.findScalarInitializer(il, ty, res, first_tok)) return true;
3691 }
3692 return false;
3693 } else if (ty.get(.@"union")) |union_ty| {
3694 if (il.*.node != .none) return false;
3695 if (actual_ty.eql(ty.*, p.comp, false)) return true;
3696 if (union_ty.data.record.fields.len == 0) {
3697 try p.errTok(.empty_aggregate_init_braces, first_tok);
3698 return error.ParsingFailed;
3699 }
3700 ty.* = union_ty.data.record.fields[0].ty;
3701 il.* = try il.*.find(p.gpa, 0);
3702 // if (il.*.node == .none and actual_ty.eql(ty, p.comp, false)) return true;
3703 if (try p.coerceArrayInitExtra(res, first_tok, ty.*, false)) return true;
3704 if (try p.findScalarInitializer(il, ty, res, first_tok)) return true;
3705 return false;
3706 }
3707 return il.*.node == .none;
3708}
3709
3710fn findAggregateInitializer(p: *Parser, il: **InitList, ty: *Type, start_index: *?u64) Error!bool {
3711 if (ty.isArray()) {
3712 if (il.*.node != .none) return false;
3713 const list_index = il.*.list.items.len;
3714 const index = if (start_index.*) |*some| blk: {
3715 some.* += 1;
3716 break :blk some.*;
3717 } else if (list_index != 0)
3718 il.*.list.items[list_index - 1].index + 1
3719 else
3720 list_index;
3721
3722 const arr_ty = ty.*;
3723 const elem_count = arr_ty.arrayLen() orelse std.math.maxInt(u64);
3724 const elem_ty = arr_ty.elemType();
3725 if (index < elem_count) {
3726 ty.* = elem_ty;
3727 il.* = try il.*.find(p.gpa, index);
3728 return true;
3729 }
3730 return false;
3731 } else if (ty.get(.@"struct")) |struct_ty| {
3732 if (il.*.node != .none) return false;
3733 const list_index = il.*.list.items.len;
3734 const index = if (start_index.*) |*some| blk: {
3735 some.* += 1;
3736 break :blk some.*;
3737 } else if (list_index != 0)
3738 il.*.list.items[list_index - 1].index + 1
3739 else
3740 list_index;
3741
3742 const field_count = struct_ty.data.record.fields.len;
3743 if (index < field_count) {
3744 ty.* = struct_ty.data.record.fields[@intCast(index)].ty;
3745 il.* = try il.*.find(p.gpa, index);
3746 return true;
3747 }
3748 return false;
3749 } else if (ty.get(.@"union")) |union_ty| {
3750 if (il.*.node != .none) return false;
3751 if (start_index.*) |_| return false; // overrides
3752 if (union_ty.data.record.fields.len == 0) return false;
3753
3754 ty.* = union_ty.data.record.fields[0].ty;
3755 il.* = try il.*.find(p.gpa, 0);
3756 return true;
3757 } else {
3758 try p.err(.too_many_scalar_init_braces);
3759 return il.*.node == .none;
3760 }
3761}
3762
3763fn coerceArrayInit(p: *Parser, item: *Result, tok: TokenIndex, target: Type) !bool {
3764 return p.coerceArrayInitExtra(item, tok, target, true);
3765}
3766
3767fn coerceArrayInitExtra(p: *Parser, item: *Result, tok: TokenIndex, target: Type, report_err: bool) !bool {
3768 if (!target.isArray()) return false;
3769
3770 const is_str_lit = p.nodeIs(item.node, .string_literal_expr);
3771 if (!is_str_lit and !p.nodeIsCompoundLiteral(item.node) or !item.ty.isArray()) {
3772 if (!report_err) return false;
3773 try p.errTok(.array_init_str, tok);
3774 return true; // do not do further coercion
3775 }
3776
3777 const target_spec = target.elemType().canonicalize(.standard).specifier;
3778 const item_spec = item.ty.elemType().canonicalize(.standard).specifier;
3779
3780 const compatible = target.elemType().eql(item.ty.elemType(), p.comp, false) or
3781 (is_str_lit and item_spec == .char and (target_spec == .uchar or target_spec == .schar)) or
3782 (is_str_lit and item_spec == .uchar and (target_spec == .uchar or target_spec == .schar or target_spec == .char));
3783 if (!compatible) {
3784 if (!report_err) return false;
3785 const e_msg = " with array of type ";
3786 try p.errStr(.incompatible_array_init, tok, try p.typePairStrExtra(target, e_msg, item.ty));
3787 return true; // do not do further coercion
3788 }
3789
3790 if (target.get(.array)) |arr_ty| {
3791 assert(item.ty.specifier == .array);
3792 const len = item.ty.arrayLen().?;
3793 const array_len = arr_ty.arrayLen().?;
3794 if (is_str_lit) {
3795 // the null byte of a string can be dropped
3796 if (len - 1 > array_len and report_err) {
3797 try p.errTok(.str_init_too_long, tok);
3798 }
3799 } else if (len > array_len and report_err) {
3800 try p.errStr(
3801 .arr_init_too_long,
3802 tok,
3803 try p.typePairStrExtra(target, " with array of type ", item.ty),
3804 );
3805 }
3806 }
3807 return true;
3808}
3809
3810fn coerceInit(p: *Parser, item: *Result, tok: TokenIndex, target: Type) !void {
3811 if (target.is(.void)) return; // Do not do type coercion on excess items
3812
3813 const node = item.node;
3814 try item.lvalConversion(p);
3815 if (target.is(.auto_type)) {
3816 if (p.getNode(node, .member_access_expr) orelse p.getNode(node, .member_access_ptr_expr)) |member_node| {
3817 if (p.tmpTree().isBitfield(member_node)) try p.errTok(.auto_type_from_bitfield, tok);
3818 }
3819 return;
3820 } else if (target.is(.c23_auto)) {
3821 return;
3822 }
3823
3824 try item.coerce(p, target, tok, .init);
3825}
3826
3827fn isStringInit(p: *Parser, ty: Type) bool {
3828 if (!ty.isArray() or !ty.elemType().isInt()) return false;
3829 var i = p.tok_i;
3830 while (true) : (i += 1) {
3831 switch (p.tok_ids[i]) {
3832 .l_paren => {},
3833 .string_literal,
3834 .string_literal_utf_16,
3835 .string_literal_utf_8,
3836 .string_literal_utf_32,
3837 .string_literal_wide,
3838 => return true,
3839 else => return false,
3840 }
3841 }
3842}
3843
3844/// Convert InitList into an AST
3845fn convertInitList(p: *Parser, il: InitList, init_ty: Type) Error!NodeIndex {
3846 const is_complex = init_ty.isComplex();
3847 if (init_ty.isScalar() and !is_complex) {
3848 if (il.node == .none) {
3849 return p.addNode(.{ .tag = .default_init_expr, .ty = init_ty, .data = undefined });
3850 }
3851 return il.node;
3852 } else if (init_ty.is(.variable_len_array)) {
3853 return error.ParsingFailed; // vla invalid, reported earlier
3854 } else if (init_ty.isArray() or is_complex) {
3855 if (il.node != .none) {
3856 return il.node;
3857 }
3858 const list_buf_top = p.list_buf.items.len;
3859 defer p.list_buf.items.len = list_buf_top;
3860
3861 const elem_ty = init_ty.elemType();
3862
3863 const max_items: u64 = init_ty.expectedInitListSize() orelse std.math.maxInt(usize);
3864 var start: u64 = 0;
3865 for (il.list.items) |*init| {
3866 if (init.index > start) {
3867 const elem = try p.addNode(.{
3868 .tag = .array_filler_expr,
3869 .ty = elem_ty,
3870 .data = .{ .int = init.index - start },
3871 });
3872 try p.list_buf.append(elem);
3873 }
3874 start = init.index + 1;
3875
3876 const elem = try p.convertInitList(init.list, elem_ty);
3877 try p.list_buf.append(elem);
3878 }
3879
3880 var arr_init_node: Tree.Node = .{
3881 .tag = .array_init_expr_two,
3882 .ty = init_ty,
3883 .data = .{ .two = .{ .none, .none } },
3884 };
3885
3886 const max_elems = p.comp.maxArrayBytes() / (@max(1, elem_ty.sizeof(p.comp) orelse 1));
3887 if (start > max_elems) {
3888 try p.errTok(.array_too_large, il.tok);
3889 start = max_elems;
3890 }
3891
3892 if (init_ty.specifier == .incomplete_array) {
3893 arr_init_node.ty.specifier = .array;
3894 arr_init_node.ty.data.array.len = start;
3895 } else if (init_ty.is(.incomplete_array)) {
3896 const arr_ty = try p.arena.create(Type.Array);
3897 arr_ty.* = .{ .elem = init_ty.elemType(), .len = start };
3898 arr_init_node.ty = .{
3899 .specifier = .array,
3900 .data = .{ .array = arr_ty },
3901 };
3902 } else if (start < max_items) {
3903 const elem = try p.addNode(.{
3904 .tag = .array_filler_expr,
3905 .ty = elem_ty,
3906 .data = .{ .int = max_items - start },
3907 });
3908 try p.list_buf.append(elem);
3909 }
3910
3911 const items = p.list_buf.items[list_buf_top..];
3912 switch (items.len) {
3913 0 => {},
3914 1 => arr_init_node.data.two[0] = items[0],
3915 2 => arr_init_node.data.two = .{ items[0], items[1] },
3916 else => {
3917 arr_init_node.tag = .array_init_expr;
3918 arr_init_node.data = .{ .range = try p.addList(items) };
3919 },
3920 }
3921 return try p.addNode(arr_init_node);
3922 } else if (init_ty.get(.@"struct")) |struct_ty| {
3923 assert(!struct_ty.hasIncompleteSize());
3924 if (il.node != .none) {
3925 return il.node;
3926 }
3927
3928 const list_buf_top = p.list_buf.items.len;
3929 defer p.list_buf.items.len = list_buf_top;
3930
3931 var init_index: usize = 0;
3932 for (struct_ty.data.record.fields, 0..) |f, i| {
3933 if (init_index < il.list.items.len and il.list.items[init_index].index == i) {
3934 const item = try p.convertInitList(il.list.items[init_index].list, f.ty);
3935 try p.list_buf.append(item);
3936 init_index += 1;
3937 } else {
3938 const item = try p.addNode(.{ .tag = .default_init_expr, .ty = f.ty, .data = undefined });
3939 try p.list_buf.append(item);
3940 }
3941 }
3942
3943 var struct_init_node: Tree.Node = .{
3944 .tag = .struct_init_expr_two,
3945 .ty = init_ty,
3946 .data = .{ .two = .{ .none, .none } },
3947 };
3948 const items = p.list_buf.items[list_buf_top..];
3949 switch (items.len) {
3950 0 => {},
3951 1 => struct_init_node.data.two[0] = items[0],
3952 2 => struct_init_node.data.two = .{ items[0], items[1] },
3953 else => {
3954 struct_init_node.tag = .struct_init_expr;
3955 struct_init_node.data = .{ .range = try p.addList(items) };
3956 },
3957 }
3958 return try p.addNode(struct_init_node);
3959 } else if (init_ty.get(.@"union")) |union_ty| {
3960 if (il.node != .none) {
3961 return il.node;
3962 }
3963
3964 var union_init_node: Tree.Node = .{
3965 .tag = .union_init_expr,
3966 .ty = init_ty,
3967 .data = .{ .union_init = .{ .field_index = 0, .node = .none } },
3968 };
3969 if (union_ty.data.record.fields.len == 0) {
3970 // do nothing for empty unions
3971 } else if (il.list.items.len == 0) {
3972 union_init_node.data.union_init.node = try p.addNode(.{
3973 .tag = .default_init_expr,
3974 .ty = init_ty,
3975 .data = undefined,
3976 });
3977 } else {
3978 const init = il.list.items[0];
3979 const index: u32 = @truncate(init.index);
3980 const field_ty = union_ty.data.record.fields[index].ty;
3981 union_init_node.data.union_init = .{
3982 .field_index = index,
3983 .node = try p.convertInitList(init.list, field_ty),
3984 };
3985 }
3986 return try p.addNode(union_init_node);
3987 } else {
3988 return error.ParsingFailed; // initializer target is invalid, reported earlier
3989 }
3990}
3991
3992fn msvcAsmStmt(p: *Parser) Error!?NodeIndex {
3993 return p.todo("MSVC assembly statements");
3994}
3995
3996/// asmOperand : ('[' IDENTIFIER ']')? asmStr '(' expr ')'
3997fn asmOperand(p: *Parser, names: *std.ArrayList(?TokenIndex), constraints: *NodeList, exprs: *NodeList) Error!void {
3998 if (p.eatToken(.l_bracket)) |l_bracket| {
3999 const ident = (try p.eatIdentifier()) orelse {
4000 try p.err(.expected_identifier);
4001 return error.ParsingFailed;
4002 };
4003 try names.append(ident);
4004 try p.expectClosing(l_bracket, .r_bracket);
4005 } else {
4006 try names.append(null);
4007 }
4008 const constraint = try p.asmStr();
4009 try constraints.append(constraint.node);
4010
4011 const l_paren = p.eatToken(.l_paren) orelse {
4012 try p.errExtra(.expected_token, p.tok_i, .{ .tok_id = .{ .actual = p.tok_ids[p.tok_i], .expected = .l_paren } });
4013 return error.ParsingFailed;
4014 };
4015 const res = try p.expr();
4016 try p.expectClosing(l_paren, .r_paren);
4017 try res.expect(p);
4018 try exprs.append(res.node);
4019}
4020
4021/// gnuAsmStmt
4022/// : asmStr
4023/// | asmStr ':' asmOperand*
4024/// | asmStr ':' asmOperand* ':' asmOperand*
4025/// | asmStr ':' asmOperand* ':' asmOperand* : asmStr? (',' asmStr)*
4026/// | asmStr ':' asmOperand* ':' asmOperand* : asmStr? (',' asmStr)* : IDENTIFIER (',' IDENTIFIER)*
4027fn gnuAsmStmt(p: *Parser, quals: Tree.GNUAssemblyQualifiers, asm_tok: TokenIndex, l_paren: TokenIndex) Error!NodeIndex {
4028 const asm_str = try p.asmStr();
4029 try p.checkAsmStr(asm_str.val, l_paren);
4030
4031 if (p.tok_ids[p.tok_i] == .r_paren) {
4032 return p.addNode(.{
4033 .tag = .gnu_asm_simple,
4034 .ty = .{ .specifier = .void },
4035 .data = .{ .un = asm_str.node },
4036 .loc = @enumFromInt(asm_tok),
4037 });
4038 }
4039
4040 const expected_items = 8; // arbitrarily chosen, most assembly will have fewer than 8 inputs/outputs/constraints/names
4041 const bytes_needed = expected_items * @sizeOf(?TokenIndex) + expected_items * 3 * @sizeOf(NodeIndex);
4042
4043 var stack_fallback = std.heap.stackFallback(bytes_needed, p.gpa);
4044 const allocator = stack_fallback.get();
4045
4046 // TODO: Consider using a TokenIndex of 0 instead of null if we need to store the names in the tree
4047 var names = std.ArrayList(?TokenIndex).initCapacity(allocator, expected_items) catch unreachable; // stack allocation already succeeded
4048 defer names.deinit();
4049 var constraints = NodeList.initCapacity(allocator, expected_items) catch unreachable; // stack allocation already succeeded
4050 defer constraints.deinit();
4051 var exprs = NodeList.initCapacity(allocator, expected_items) catch unreachable; //stack allocation already succeeded
4052 defer exprs.deinit();
4053 var clobbers = NodeList.initCapacity(allocator, expected_items) catch unreachable; //stack allocation already succeeded
4054 defer clobbers.deinit();
4055
4056 // Outputs
4057 var ate_extra_colon = false;
4058 if (p.eatToken(.colon) orelse p.eatToken(.colon_colon)) |tok_i| {
4059 ate_extra_colon = p.tok_ids[tok_i] == .colon_colon;
4060 if (!ate_extra_colon) {
4061 if (p.tok_ids[p.tok_i].isStringLiteral() or p.tok_ids[p.tok_i] == .l_bracket) {
4062 while (true) {
4063 try p.asmOperand(&names, &constraints, &exprs);
4064 if (p.eatToken(.comma) == null) break;
4065 }
4066 }
4067 }
4068 }
4069
4070 const num_outputs = names.items.len;
4071
4072 // Inputs
4073 if (ate_extra_colon or p.tok_ids[p.tok_i] == .colon or p.tok_ids[p.tok_i] == .colon_colon) {
4074 if (ate_extra_colon) {
4075 ate_extra_colon = false;
4076 } else {
4077 ate_extra_colon = p.tok_ids[p.tok_i] == .colon_colon;
4078 p.tok_i += 1;
4079 }
4080 if (!ate_extra_colon) {
4081 if (p.tok_ids[p.tok_i].isStringLiteral() or p.tok_ids[p.tok_i] == .l_bracket) {
4082 while (true) {
4083 try p.asmOperand(&names, &constraints, &exprs);
4084 if (p.eatToken(.comma) == null) break;
4085 }
4086 }
4087 }
4088 }
4089 std.debug.assert(names.items.len == constraints.items.len and constraints.items.len == exprs.items.len);
4090 const num_inputs = names.items.len - num_outputs;
4091 _ = num_inputs;
4092
4093 // Clobbers
4094 if (ate_extra_colon or p.tok_ids[p.tok_i] == .colon or p.tok_ids[p.tok_i] == .colon_colon) {
4095 if (ate_extra_colon) {
4096 ate_extra_colon = false;
4097 } else {
4098 ate_extra_colon = p.tok_ids[p.tok_i] == .colon_colon;
4099 p.tok_i += 1;
4100 }
4101 if (!ate_extra_colon and p.tok_ids[p.tok_i].isStringLiteral()) {
4102 while (true) {
4103 const clobber = try p.asmStr();
4104 try clobbers.append(clobber.node);
4105 if (p.eatToken(.comma) == null) break;
4106 }
4107 }
4108 }
4109
4110 if (!quals.goto and (p.tok_ids[p.tok_i] != .r_paren or ate_extra_colon)) {
4111 try p.errExtra(.expected_token, p.tok_i, .{ .tok_id = .{ .actual = p.tok_ids[p.tok_i], .expected = .r_paren } });
4112 return error.ParsingFailed;
4113 }
4114
4115 // Goto labels
4116 var num_labels: u32 = 0;
4117 if (ate_extra_colon or p.tok_ids[p.tok_i] == .colon) {
4118 if (!ate_extra_colon) {
4119 p.tok_i += 1;
4120 }
4121 while (true) {
4122 const ident = (try p.eatIdentifier()) orelse {
4123 try p.err(.expected_identifier);
4124 return error.ParsingFailed;
4125 };
4126 const ident_str = p.tokSlice(ident);
4127 const label = p.findLabel(ident_str) orelse blk: {
4128 try p.labels.append(.{ .unresolved_goto = ident });
4129 break :blk ident;
4130 };
4131 try names.append(ident);
4132
4133 const elem_ty = try p.arena.create(Type);
4134 elem_ty.* = .{ .specifier = .void };
4135 const result_ty = Type{ .specifier = .pointer, .data = .{ .sub_type = elem_ty } };
4136
4137 const label_addr_node = try p.addNode(.{
4138 .tag = .addr_of_label,
4139 .data = .{ .decl_ref = label },
4140 .ty = result_ty,
4141 .loc = @enumFromInt(ident),
4142 });
4143 try exprs.append(label_addr_node);
4144
4145 num_labels += 1;
4146 if (p.eatToken(.comma) == null) break;
4147 }
4148 } else if (quals.goto) {
4149 try p.errExtra(.expected_token, p.tok_i, .{ .tok_id = .{ .actual = p.tok_ids[p.tok_i], .expected = .colon } });
4150 return error.ParsingFailed;
4151 }
4152
4153 // TODO: validate and insert into AST
4154 return .none;
4155}
4156
4157fn checkAsmStr(p: *Parser, asm_str: Value, tok: TokenIndex) !void {
4158 if (!p.comp.langopts.gnu_asm) {
4159 const str = p.comp.interner.get(asm_str.ref()).bytes;
4160 if (str.len > 1) {
4161 // Empty string (just a NUL byte) is ok because it does not emit any assembly
4162 try p.errTok(.gnu_asm_disabled, tok);
4163 }
4164 }
4165}
4166
4167/// assembly
4168/// : keyword_asm asmQual* '(' asmStr ')'
4169/// | keyword_asm asmQual* '(' gnuAsmStmt ')'
4170/// | keyword_asm msvcAsmStmt
4171fn assembly(p: *Parser, kind: enum { global, decl_label, stmt }) Error!?NodeIndex {
4172 const asm_tok = p.tok_i;
4173 switch (p.tok_ids[p.tok_i]) {
4174 .keyword_asm => {
4175 try p.err(.extension_token_used);
4176 p.tok_i += 1;
4177 },
4178 .keyword_asm1, .keyword_asm2 => p.tok_i += 1,
4179 else => return null,
4180 }
4181
4182 if (!p.tok_ids[p.tok_i].canOpenGCCAsmStmt()) {
4183 return p.msvcAsmStmt();
4184 }
4185
4186 var quals: Tree.GNUAssemblyQualifiers = .{};
4187 while (true) : (p.tok_i += 1) switch (p.tok_ids[p.tok_i]) {
4188 .keyword_volatile, .keyword_volatile1, .keyword_volatile2 => {
4189 if (kind != .stmt) try p.errStr(.meaningless_asm_qual, p.tok_i, "volatile");
4190 if (quals.@"volatile") try p.errStr(.duplicate_asm_qual, p.tok_i, "volatile");
4191 quals.@"volatile" = true;
4192 },
4193 .keyword_inline, .keyword_inline1, .keyword_inline2 => {
4194 if (kind != .stmt) try p.errStr(.meaningless_asm_qual, p.tok_i, "inline");
4195 if (quals.@"inline") try p.errStr(.duplicate_asm_qual, p.tok_i, "inline");
4196 quals.@"inline" = true;
4197 },
4198 .keyword_goto => {
4199 if (kind != .stmt) try p.errStr(.meaningless_asm_qual, p.tok_i, "goto");
4200 if (quals.goto) try p.errStr(.duplicate_asm_qual, p.tok_i, "goto");
4201 quals.goto = true;
4202 },
4203 else => break,
4204 };
4205
4206 const l_paren = try p.expectToken(.l_paren);
4207 var result_node: NodeIndex = .none;
4208 switch (kind) {
4209 .decl_label => {
4210 const asm_str = try p.asmStr();
4211 const str = try p.removeNull(asm_str.val);
4212
4213 const attr = Attribute{ .tag = .asm_label, .args = .{ .asm_label = .{ .name = str } }, .syntax = .keyword };
4214 try p.attr_buf.append(p.gpa, .{ .attr = attr, .tok = asm_tok });
4215 },
4216 .global => {
4217 const asm_str = try p.asmStr();
4218 try p.checkAsmStr(asm_str.val, l_paren);
4219 result_node = try p.addNode(.{
4220 .tag = .file_scope_asm,
4221 .ty = .{ .specifier = .void },
4222 .data = .{ .decl = .{ .name = asm_tok, .node = asm_str.node } },
4223 .loc = @enumFromInt(asm_tok),
4224 });
4225 },
4226 .stmt => result_node = try p.gnuAsmStmt(quals, asm_tok, l_paren),
4227 }
4228 try p.expectClosing(l_paren, .r_paren);
4229
4230 if (kind != .decl_label) _ = try p.expectToken(.semicolon);
4231 return result_node;
4232}
4233
4234/// Same as stringLiteral but errors on unicode and wide string literals
4235fn asmStr(p: *Parser) Error!Result {
4236 var i = p.tok_i;
4237 while (true) : (i += 1) switch (p.tok_ids[i]) {
4238 .string_literal, .unterminated_string_literal => {},
4239 .string_literal_utf_16, .string_literal_utf_8, .string_literal_utf_32 => {
4240 try p.errStr(.invalid_asm_str, p.tok_i, "unicode");
4241 return error.ParsingFailed;
4242 },
4243 .string_literal_wide => {
4244 try p.errStr(.invalid_asm_str, p.tok_i, "wide");
4245 return error.ParsingFailed;
4246 },
4247 else => {
4248 if (i == p.tok_i) {
4249 try p.errStr(.expected_str_literal_in, p.tok_i, "asm");
4250 return error.ParsingFailed;
4251 }
4252 break;
4253 },
4254 };
4255 return try p.stringLiteral();
4256}
4257
4258// ====== statements ======
4259
4260/// stmt
4261/// : labeledStmt
4262/// | compoundStmt
4263/// | keyword_if '(' expr ')' stmt (keyword_else stmt)?
4264/// | keyword_switch '(' expr ')' stmt
4265/// | keyword_while '(' expr ')' stmt
4266/// | keyword_do stmt while '(' expr ')' ';'
4267/// | keyword_for '(' (decl | expr? ';') expr? ';' expr? ')' stmt
4268/// | keyword_goto (IDENTIFIER | ('*' expr)) ';'
4269/// | keyword_continue ';'
4270/// | keyword_break ';'
4271/// | keyword_return expr? ';'
4272/// | assembly ';'
4273/// | expr? ';'
4274fn stmt(p: *Parser) Error!NodeIndex {
4275 if (try p.labeledStmt()) |some| return some;
4276 if (try p.compoundStmt(false, null)) |some| return some;
4277 if (p.eatToken(.keyword_if)) |kw_if| {
4278 const l_paren = try p.expectToken(.l_paren);
4279 const cond_tok = p.tok_i;
4280 var cond = try p.expr();
4281 try cond.expect(p);
4282 try cond.lvalConversion(p);
4283 try cond.usualUnaryConversion(p, cond_tok);
4284 if (!cond.ty.isScalar())
4285 try p.errStr(.statement_scalar, l_paren + 1, try p.typeStr(cond.ty));
4286 try cond.saveValue(p);
4287 try p.expectClosing(l_paren, .r_paren);
4288
4289 const then = try p.stmt();
4290 const @"else" = if (p.eatToken(.keyword_else)) |_| try p.stmt() else .none;
4291
4292 if (then != .none and @"else" != .none)
4293 return try p.addNode(.{
4294 .tag = .if_then_else_stmt,
4295 .data = .{ .if3 = .{ .cond = cond.node, .body = (try p.addList(&.{ then, @"else" })).start } },
4296 .loc = @enumFromInt(kw_if),
4297 })
4298 else
4299 return try p.addNode(.{
4300 .tag = .if_then_stmt,
4301 .data = .{ .bin = .{ .lhs = cond.node, .rhs = then } },
4302 .loc = @enumFromInt(kw_if),
4303 });
4304 }
4305 if (p.eatToken(.keyword_switch)) |kw_switch| {
4306 const l_paren = try p.expectToken(.l_paren);
4307 const cond_tok = p.tok_i;
4308 var cond = try p.expr();
4309 try cond.expect(p);
4310 try cond.lvalConversion(p);
4311 try cond.usualUnaryConversion(p, cond_tok);
4312
4313 if (!cond.ty.isInt())
4314 try p.errStr(.statement_int, l_paren + 1, try p.typeStr(cond.ty));
4315 try cond.saveValue(p);
4316 try p.expectClosing(l_paren, .r_paren);
4317
4318 const old_switch = p.@"switch";
4319 var @"switch" = Switch{
4320 .ranges = std.ArrayList(Switch.Range).init(p.gpa),
4321 .ty = cond.ty,
4322 .comp = p.comp,
4323 };
4324 p.@"switch" = &@"switch";
4325 defer {
4326 @"switch".ranges.deinit();
4327 p.@"switch" = old_switch;
4328 }
4329
4330 const body = try p.stmt();
4331
4332 return try p.addNode(.{
4333 .tag = .switch_stmt,
4334 .data = .{ .bin = .{ .lhs = cond.node, .rhs = body } },
4335 .loc = @enumFromInt(kw_switch),
4336 });
4337 }
4338 if (p.eatToken(.keyword_while)) |kw_while| {
4339 const l_paren = try p.expectToken(.l_paren);
4340 const cond_tok = p.tok_i;
4341 var cond = try p.expr();
4342 try cond.expect(p);
4343 try cond.lvalConversion(p);
4344 try cond.usualUnaryConversion(p, cond_tok);
4345 if (!cond.ty.isScalar())
4346 try p.errStr(.statement_scalar, l_paren + 1, try p.typeStr(cond.ty));
4347 try cond.saveValue(p);
4348 try p.expectClosing(l_paren, .r_paren);
4349
4350 const body = body: {
4351 const old_loop = p.in_loop;
4352 p.in_loop = true;
4353 defer p.in_loop = old_loop;
4354 break :body try p.stmt();
4355 };
4356
4357 return try p.addNode(.{
4358 .tag = .while_stmt,
4359 .data = .{ .bin = .{ .lhs = cond.node, .rhs = body } },
4360 .loc = @enumFromInt(kw_while),
4361 });
4362 }
4363 if (p.eatToken(.keyword_do)) |kw_do| {
4364 const body = body: {
4365 const old_loop = p.in_loop;
4366 p.in_loop = true;
4367 defer p.in_loop = old_loop;
4368 break :body try p.stmt();
4369 };
4370
4371 _ = try p.expectToken(.keyword_while);
4372 const l_paren = try p.expectToken(.l_paren);
4373 const cond_tok = p.tok_i;
4374 var cond = try p.expr();
4375 try cond.expect(p);
4376 try cond.lvalConversion(p);
4377 try cond.usualUnaryConversion(p, cond_tok);
4378
4379 if (!cond.ty.isScalar())
4380 try p.errStr(.statement_scalar, l_paren + 1, try p.typeStr(cond.ty));
4381 try cond.saveValue(p);
4382 try p.expectClosing(l_paren, .r_paren);
4383
4384 _ = try p.expectToken(.semicolon);
4385 return try p.addNode(.{
4386 .tag = .do_while_stmt,
4387 .data = .{ .bin = .{ .lhs = cond.node, .rhs = body } },
4388 .loc = @enumFromInt(kw_do),
4389 });
4390 }
4391 if (p.eatToken(.keyword_for)) |kw_for| {
4392 try p.syms.pushScope(p);
4393 defer p.syms.popScope();
4394 const decl_buf_top = p.decl_buf.items.len;
4395 defer p.decl_buf.items.len = decl_buf_top;
4396
4397 const l_paren = try p.expectToken(.l_paren);
4398 const got_decl = try p.decl();
4399
4400 // for (init
4401 const init_start = p.tok_i;
4402 var err_start = p.comp.diagnostics.list.items.len;
4403 var init = if (!got_decl) try p.expr() else Result{};
4404 try init.saveValue(p);
4405 try init.maybeWarnUnused(p, init_start, err_start);
4406 if (!got_decl) _ = try p.expectToken(.semicolon);
4407
4408 // for (init; cond
4409 const cond_tok = p.tok_i;
4410 var cond = try p.expr();
4411 if (cond.node != .none) {
4412 try cond.lvalConversion(p);
4413 try cond.usualUnaryConversion(p, cond_tok);
4414 if (!cond.ty.isScalar())
4415 try p.errStr(.statement_scalar, l_paren + 1, try p.typeStr(cond.ty));
4416 }
4417 try cond.saveValue(p);
4418 _ = try p.expectToken(.semicolon);
4419
4420 // for (init; cond; incr
4421 const incr_start = p.tok_i;
4422 err_start = p.comp.diagnostics.list.items.len;
4423 var incr = try p.expr();
4424 try incr.maybeWarnUnused(p, incr_start, err_start);
4425 try incr.saveValue(p);
4426 try p.expectClosing(l_paren, .r_paren);
4427
4428 const body = body: {
4429 const old_loop = p.in_loop;
4430 p.in_loop = true;
4431 defer p.in_loop = old_loop;
4432 break :body try p.stmt();
4433 };
4434
4435 if (got_decl) {
4436 const start = (try p.addList(p.decl_buf.items[decl_buf_top..])).start;
4437 const end = (try p.addList(&.{ cond.node, incr.node, body })).end;
4438
4439 return try p.addNode(.{
4440 .tag = .for_decl_stmt,
4441 .data = .{ .range = .{ .start = start, .end = end } },
4442 .loc = @enumFromInt(kw_for),
4443 });
4444 } else if (init.node == .none and cond.node == .none and incr.node == .none) {
4445 return try p.addNode(.{
4446 .tag = .forever_stmt,
4447 .data = .{ .un = body },
4448 .loc = @enumFromInt(kw_for),
4449 });
4450 } else return try p.addNode(.{
4451 .tag = .for_stmt,
4452 .data = .{ .if3 = .{
4453 .cond = body,
4454 .body = (try p.addList(&.{ init.node, cond.node, incr.node })).start,
4455 } },
4456 .loc = @enumFromInt(kw_for),
4457 });
4458 }
4459 if (p.eatToken(.keyword_goto)) |goto_tok| {
4460 if (p.eatToken(.asterisk)) |_| {
4461 const expr_tok = p.tok_i;
4462 var e = try p.expr();
4463 try e.expect(p);
4464 try e.lvalConversion(p);
4465 p.computed_goto_tok = p.computed_goto_tok orelse goto_tok;
4466 if (!e.ty.isPtr()) {
4467 const elem_ty = try p.arena.create(Type);
4468 elem_ty.* = .{ .specifier = .void, .qual = .{ .@"const" = true } };
4469 const result_ty = Type{
4470 .specifier = .pointer,
4471 .data = .{ .sub_type = elem_ty },
4472 };
4473 if (!e.ty.isInt()) {
4474 try p.errStr(.incompatible_arg, expr_tok, try p.typePairStrExtra(e.ty, " to parameter of incompatible type ", result_ty));
4475 return error.ParsingFailed;
4476 }
4477 if (e.val.isZero(p.comp)) {
4478 try e.nullCast(p, result_ty);
4479 } else {
4480 try p.errStr(.implicit_int_to_ptr, expr_tok, try p.typePairStrExtra(e.ty, " to ", result_ty));
4481 try e.ptrCast(p, result_ty);
4482 }
4483 }
4484
4485 try e.un(p, .computed_goto_stmt, goto_tok);
4486 _ = try p.expectToken(.semicolon);
4487 return e.node;
4488 }
4489 const name_tok = try p.expectIdentifier();
4490 const str = p.tokSlice(name_tok);
4491 if (p.findLabel(str) == null) {
4492 try p.labels.append(.{ .unresolved_goto = name_tok });
4493 }
4494 _ = try p.expectToken(.semicolon);
4495 return try p.addNode(.{
4496 .tag = .goto_stmt,
4497 .data = .{ .decl_ref = name_tok },
4498 .loc = @enumFromInt(goto_tok),
4499 });
4500 }
4501 if (p.eatToken(.keyword_continue)) |cont| {
4502 if (!p.in_loop) try p.errTok(.continue_not_in_loop, cont);
4503 _ = try p.expectToken(.semicolon);
4504 return try p.addNode(.{ .tag = .continue_stmt, .data = undefined, .loc = @enumFromInt(cont) });
4505 }
4506 if (p.eatToken(.keyword_break)) |br| {
4507 if (!p.in_loop and p.@"switch" == null) try p.errTok(.break_not_in_loop_or_switch, br);
4508 _ = try p.expectToken(.semicolon);
4509 return try p.addNode(.{ .tag = .break_stmt, .data = undefined, .loc = @enumFromInt(br) });
4510 }
4511 if (try p.returnStmt()) |some| return some;
4512 if (try p.assembly(.stmt)) |some| return some;
4513
4514 const expr_start = p.tok_i;
4515 const err_start = p.comp.diagnostics.list.items.len;
4516
4517 const e = try p.expr();
4518 if (e.node != .none) {
4519 _ = try p.expectToken(.semicolon);
4520 try e.maybeWarnUnused(p, expr_start, err_start);
4521 return e.node;
4522 }
4523
4524 const attr_buf_top = p.attr_buf.len;
4525 defer p.attr_buf.len = attr_buf_top;
4526 try p.attributeSpecifier();
4527
4528 if (p.eatToken(.semicolon)) |semicolon| {
4529 var null_node: Tree.Node = .{ .tag = .null_stmt, .data = undefined, .loc = @enumFromInt(semicolon) };
4530 null_node.ty = try Attribute.applyStatementAttributes(p, null_node.ty, expr_start, attr_buf_top);
4531 return p.addNode(null_node);
4532 }
4533
4534 try p.err(.expected_stmt);
4535 return error.ParsingFailed;
4536}
4537
4538/// labeledStmt
4539/// : IDENTIFIER ':' stmt
4540/// | keyword_case integerConstExpr ':' stmt
4541/// | keyword_default ':' stmt
4542fn labeledStmt(p: *Parser) Error!?NodeIndex {
4543 if ((p.tok_ids[p.tok_i] == .identifier or p.tok_ids[p.tok_i] == .extended_identifier) and p.tok_ids[p.tok_i + 1] == .colon) {
4544 const name_tok = try p.expectIdentifier();
4545 const str = p.tokSlice(name_tok);
4546 if (p.findLabel(str)) |some| {
4547 try p.errStr(.duplicate_label, name_tok, str);
4548 try p.errStr(.previous_label, some, str);
4549 } else {
4550 p.label_count += 1;
4551 try p.labels.append(.{ .label = name_tok });
4552 var i: usize = 0;
4553 while (i < p.labels.items.len) {
4554 if (p.labels.items[i] == .unresolved_goto and
4555 mem.eql(u8, p.tokSlice(p.labels.items[i].unresolved_goto), str))
4556 {
4557 _ = p.labels.swapRemove(i);
4558 } else i += 1;
4559 }
4560 }
4561
4562 p.tok_i += 1;
4563 const attr_buf_top = p.attr_buf.len;
4564 defer p.attr_buf.len = attr_buf_top;
4565 try p.attributeSpecifier();
4566
4567 var labeled_stmt = Tree.Node{
4568 .tag = .labeled_stmt,
4569 .data = .{ .decl = .{ .name = name_tok, .node = try p.labelableStmt() } },
4570 .loc = @enumFromInt(name_tok),
4571 };
4572 labeled_stmt.ty = try Attribute.applyLabelAttributes(p, labeled_stmt.ty, attr_buf_top);
4573 return try p.addNode(labeled_stmt);
4574 } else if (p.eatToken(.keyword_case)) |case| {
4575 const first_item = try p.integerConstExpr(.gnu_folding_extension);
4576 const ellipsis = p.tok_i;
4577 const second_item = if (p.eatToken(.ellipsis) != null) blk: {
4578 try p.errTok(.gnu_switch_range, ellipsis);
4579 break :blk try p.integerConstExpr(.gnu_folding_extension);
4580 } else null;
4581 _ = try p.expectToken(.colon);
4582
4583 if (p.@"switch") |some| check: {
4584 if (some.ty.hasIncompleteSize()) break :check; // error already reported for incomplete size
4585
4586 const first = first_item.val;
4587 const last = if (second_item) |second| second.val else first;
4588 if (first.opt_ref == .none) {
4589 try p.errTok(.case_val_unavailable, case + 1);
4590 break :check;
4591 } else if (last.opt_ref == .none) {
4592 try p.errTok(.case_val_unavailable, ellipsis + 1);
4593 break :check;
4594 } else if (last.compare(.lt, first, p.comp)) {
4595 try p.errTok(.empty_case_range, case + 1);
4596 break :check;
4597 }
4598
4599 // TODO cast to target type
4600 const prev = (try some.add(first, last, case + 1)) orelse break :check;
4601
4602 // TODO check which value was already handled
4603 try p.errStr(.duplicate_switch_case, case + 1, try first_item.str(p));
4604 try p.errTok(.previous_case, prev.tok);
4605 } else {
4606 try p.errStr(.case_not_in_switch, case, "case");
4607 }
4608
4609 const s = try p.labelableStmt();
4610 if (second_item) |some| return try p.addNode(.{
4611 .tag = .case_range_stmt,
4612 .data = .{ .if3 = .{ .cond = s, .body = (try p.addList(&.{ first_item.node, some.node })).start } },
4613 .loc = @enumFromInt(case),
4614 }) else return try p.addNode(.{
4615 .tag = .case_stmt,
4616 .data = .{ .bin = .{ .lhs = first_item.node, .rhs = s } },
4617 .loc = @enumFromInt(case),
4618 });
4619 } else if (p.eatToken(.keyword_default)) |default| {
4620 _ = try p.expectToken(.colon);
4621 const s = try p.labelableStmt();
4622 const node = try p.addNode(.{
4623 .tag = .default_stmt,
4624 .data = .{ .un = s },
4625 .loc = @enumFromInt(default),
4626 });
4627 const @"switch" = p.@"switch" orelse {
4628 try p.errStr(.case_not_in_switch, default, "default");
4629 return node;
4630 };
4631 if (@"switch".default) |previous| {
4632 try p.errTok(.multiple_default, default);
4633 try p.errTok(.previous_case, previous);
4634 } else {
4635 @"switch".default = default;
4636 }
4637 return node;
4638 } else return null;
4639}
4640
4641fn labelableStmt(p: *Parser) Error!NodeIndex {
4642 if (p.tok_ids[p.tok_i] == .r_brace) {
4643 try p.err(.label_compound_end);
4644 return p.addNode(.{ .tag = .null_stmt, .data = undefined, .loc = @enumFromInt(p.tok_i) });
4645 }
4646 return p.stmt();
4647}
4648
4649const StmtExprState = struct {
4650 last_expr_tok: TokenIndex = 0,
4651 last_expr_res: Result = .{ .ty = .{ .specifier = .void } },
4652};
4653
4654/// compoundStmt : '{' ( decl | keyword_extension decl | staticAssert | stmt)* '}'
4655fn compoundStmt(p: *Parser, is_fn_body: bool, stmt_expr_state: ?*StmtExprState) Error!?NodeIndex {
4656 const l_brace = p.eatToken(.l_brace) orelse return null;
4657
4658 const decl_buf_top = p.decl_buf.items.len;
4659 defer p.decl_buf.items.len = decl_buf_top;
4660
4661 // the parameters of a function are in the same scope as the body
4662 if (!is_fn_body) try p.syms.pushScope(p);
4663 defer if (!is_fn_body) p.syms.popScope();
4664
4665 var noreturn_index: ?TokenIndex = null;
4666 var noreturn_label_count: u32 = 0;
4667
4668 while (p.eatToken(.r_brace) == null) : (_ = try p.pragma()) {
4669 if (stmt_expr_state) |state| state.* = .{};
4670 if (try p.parseOrNextStmt(staticAssert, l_brace)) continue;
4671 if (try p.parseOrNextStmt(decl, l_brace)) continue;
4672 if (p.eatToken(.keyword_extension)) |ext| {
4673 const saved_extension = p.extension_suppressed;
4674 defer p.extension_suppressed = saved_extension;
4675 p.extension_suppressed = true;
4676
4677 if (try p.parseOrNextStmt(decl, l_brace)) continue;
4678 p.tok_i = ext;
4679 }
4680 const stmt_tok = p.tok_i;
4681 const s = p.stmt() catch |er| switch (er) {
4682 error.ParsingFailed => {
4683 try p.nextStmt(l_brace);
4684 continue;
4685 },
4686 else => |e| return e,
4687 };
4688 if (s == .none) continue;
4689 if (stmt_expr_state) |state| {
4690 state.* = .{
4691 .last_expr_tok = stmt_tok,
4692 .last_expr_res = .{
4693 .node = s,
4694 .ty = p.nodes.items(.ty)[@intFromEnum(s)],
4695 },
4696 };
4697 }
4698 try p.decl_buf.append(s);
4699
4700 if (noreturn_index == null and p.nodeIsNoreturn(s) == .yes) {
4701 noreturn_index = p.tok_i;
4702 noreturn_label_count = p.label_count;
4703 }
4704 switch (p.nodes.items(.tag)[@intFromEnum(s)]) {
4705 .case_stmt, .default_stmt, .labeled_stmt => noreturn_index = null,
4706 else => {},
4707 }
4708 }
4709 const r_brace = p.tok_i - 1;
4710
4711 if (noreturn_index) |some| {
4712 // if new labels were defined we cannot be certain that the code is unreachable
4713 if (some != p.tok_i - 1 and noreturn_label_count == p.label_count) try p.errTok(.unreachable_code, some);
4714 }
4715 if (is_fn_body) {
4716 const last_noreturn = if (p.decl_buf.items.len == decl_buf_top)
4717 .no
4718 else
4719 p.nodeIsNoreturn(p.decl_buf.items[p.decl_buf.items.len - 1]);
4720
4721 if (last_noreturn != .yes) {
4722 const ret_ty = p.func.ty.?.returnType();
4723 var return_zero = false;
4724 if (last_noreturn == .no and !ret_ty.is(.void) and !ret_ty.isFunc() and !ret_ty.isArray()) {
4725 const func_name = p.tokSlice(p.func.name);
4726 const interned_name = try StrInt.intern(p.comp, func_name);
4727 if (interned_name == p.string_ids.main_id and ret_ty.is(.int)) {
4728 return_zero = true;
4729 } else {
4730 try p.errStr(.func_does_not_return, p.tok_i - 1, func_name);
4731 }
4732 }
4733 try p.decl_buf.append(try p.addNode(.{ .tag = .implicit_return, .ty = p.func.ty.?.returnType(), .data = .{ .return_zero = return_zero }, .loc = @enumFromInt(r_brace) }));
4734 }
4735 if (p.func.ident) |some| try p.decl_buf.insert(decl_buf_top, some.node);
4736 if (p.func.pretty_ident) |some| try p.decl_buf.insert(decl_buf_top, some.node);
4737 }
4738
4739 var node: Tree.Node = .{
4740 .tag = .compound_stmt_two,
4741 .data = .{ .two = .{ .none, .none } },
4742 .loc = @enumFromInt(l_brace),
4743 };
4744 const statements = p.decl_buf.items[decl_buf_top..];
4745 switch (statements.len) {
4746 0 => {},
4747 1 => node.data = .{ .two = .{ statements[0], .none } },
4748 2 => node.data = .{ .two = .{ statements[0], statements[1] } },
4749 else => {
4750 node.tag = .compound_stmt;
4751 node.data = .{ .range = try p.addList(statements) };
4752 },
4753 }
4754 return try p.addNode(node);
4755}
4756
4757const NoreturnKind = enum { no, yes, complex };
4758
4759fn nodeIsNoreturn(p: *Parser, node: NodeIndex) NoreturnKind {
4760 switch (p.nodes.items(.tag)[@intFromEnum(node)]) {
4761 .break_stmt, .continue_stmt, .return_stmt => return .yes,
4762 .if_then_else_stmt => {
4763 const data = p.data.items[p.nodes.items(.data)[@intFromEnum(node)].if3.body..];
4764 const then_type = p.nodeIsNoreturn(data[0]);
4765 const else_type = p.nodeIsNoreturn(data[1]);
4766 if (then_type == .complex or else_type == .complex) return .complex;
4767 if (then_type == .yes and else_type == .yes) return .yes;
4768 return .no;
4769 },
4770 .compound_stmt_two => {
4771 const data = p.nodes.items(.data)[@intFromEnum(node)];
4772 const lhs_type = if (data.two[0] != .none) p.nodeIsNoreturn(data.two[0]) else .no;
4773 const rhs_type = if (data.two[1] != .none) p.nodeIsNoreturn(data.two[1]) else .no;
4774 if (lhs_type == .complex or rhs_type == .complex) return .complex;
4775 if (lhs_type == .yes or rhs_type == .yes) return .yes;
4776 return .no;
4777 },
4778 .compound_stmt => {
4779 const data = p.nodes.items(.data)[@intFromEnum(node)];
4780 var it = data.range.start;
4781 while (it != data.range.end) : (it += 1) {
4782 const kind = p.nodeIsNoreturn(p.data.items[it]);
4783 if (kind != .no) return kind;
4784 }
4785 return .no;
4786 },
4787 .labeled_stmt => {
4788 const data = p.nodes.items(.data)[@intFromEnum(node)];
4789 return p.nodeIsNoreturn(data.decl.node);
4790 },
4791 .default_stmt => {
4792 const data = p.nodes.items(.data)[@intFromEnum(node)];
4793 if (data.un == .none) return .no;
4794 return p.nodeIsNoreturn(data.un);
4795 },
4796 .while_stmt, .do_while_stmt, .for_decl_stmt, .forever_stmt, .for_stmt, .switch_stmt => return .complex,
4797 else => return .no,
4798 }
4799}
4800
4801fn parseOrNextStmt(p: *Parser, comptime func: fn (*Parser) Error!bool, l_brace: TokenIndex) !bool {
4802 return func(p) catch |er| switch (er) {
4803 error.ParsingFailed => {
4804 try p.nextStmt(l_brace);
4805 return true;
4806 },
4807 else => |e| return e,
4808 };
4809}
4810
4811fn nextStmt(p: *Parser, l_brace: TokenIndex) !void {
4812 var parens: u32 = 0;
4813 while (p.tok_i < p.tok_ids.len) : (p.tok_i += 1) {
4814 switch (p.tok_ids[p.tok_i]) {
4815 .l_paren, .l_brace, .l_bracket => parens += 1,
4816 .r_paren, .r_bracket => if (parens != 0) {
4817 parens -= 1;
4818 },
4819 .r_brace => if (parens == 0)
4820 return
4821 else {
4822 parens -= 1;
4823 },
4824 .semicolon => if (parens == 0) {
4825 p.tok_i += 1;
4826 return;
4827 },
4828 .keyword_for,
4829 .keyword_while,
4830 .keyword_do,
4831 .keyword_if,
4832 .keyword_goto,
4833 .keyword_switch,
4834 .keyword_case,
4835 .keyword_default,
4836 .keyword_continue,
4837 .keyword_break,
4838 .keyword_return,
4839 .keyword_typedef,
4840 .keyword_extern,
4841 .keyword_static,
4842 .keyword_auto,
4843 .keyword_register,
4844 .keyword_thread_local,
4845 .keyword_c23_thread_local,
4846 .keyword_inline,
4847 .keyword_inline1,
4848 .keyword_inline2,
4849 .keyword_noreturn,
4850 .keyword_void,
4851 .keyword_bool,
4852 .keyword_c23_bool,
4853 .keyword_char,
4854 .keyword_short,
4855 .keyword_int,
4856 .keyword_long,
4857 .keyword_signed,
4858 .keyword_signed1,
4859 .keyword_signed2,
4860 .keyword_unsigned,
4861 .keyword_float,
4862 .keyword_double,
4863 .keyword_complex,
4864 .keyword_atomic,
4865 .keyword_enum,
4866 .keyword_struct,
4867 .keyword_union,
4868 .keyword_alignas,
4869 .keyword_c23_alignas,
4870 .keyword_typeof,
4871 .keyword_typeof1,
4872 .keyword_typeof2,
4873 .keyword_typeof_unqual,
4874 .keyword_extension,
4875 => if (parens == 0) return,
4876 .keyword_pragma => p.skipToPragmaSentinel(),
4877 else => {},
4878 }
4879 }
4880 p.tok_i -= 1; // So we can consume EOF
4881 try p.expectClosing(l_brace, .r_brace);
4882 unreachable;
4883}
4884
4885fn returnStmt(p: *Parser) Error!?NodeIndex {
4886 const ret_tok = p.eatToken(.keyword_return) orelse return null;
4887
4888 const e_tok = p.tok_i;
4889 var e = try p.expr();
4890 _ = try p.expectToken(.semicolon);
4891 const ret_ty = p.func.ty.?.returnType();
4892
4893 if (p.func.ty.?.hasAttribute(.noreturn)) {
4894 try p.errStr(.invalid_noreturn, e_tok, p.tokSlice(p.func.name));
4895 }
4896
4897 if (e.node == .none) {
4898 if (!ret_ty.is(.void)) try p.errStr(.func_should_return, ret_tok, p.tokSlice(p.func.name));
4899 return try p.addNode(.{ .tag = .return_stmt, .data = .{ .un = e.node }, .loc = @enumFromInt(ret_tok) });
4900 } else if (ret_ty.is(.void)) {
4901 try p.errStr(.void_func_returns_value, e_tok, p.tokSlice(p.func.name));
4902 return try p.addNode(.{ .tag = .return_stmt, .data = .{ .un = e.node }, .loc = @enumFromInt(ret_tok) });
4903 }
4904
4905 try e.lvalConversion(p);
4906 try e.coerce(p, ret_ty, e_tok, .ret);
4907
4908 try e.saveValue(p);
4909 return try p.addNode(.{ .tag = .return_stmt, .data = .{ .un = e.node }, .loc = @enumFromInt(ret_tok) });
4910}
4911
4912// ====== expressions ======
4913
4914pub fn macroExpr(p: *Parser) Compilation.Error!bool {
4915 const res = p.condExpr() catch |e| switch (e) {
4916 error.OutOfMemory => return error.OutOfMemory,
4917 error.FatalError => return error.FatalError,
4918 error.ParsingFailed => return false,
4919 };
4920 if (res.val.opt_ref == .none) {
4921 try p.errTok(.expected_expr, p.tok_i);
4922 return false;
4923 }
4924 return res.val.toBool(p.comp);
4925}
4926
4927const CallExpr = union(enum) {
4928 standard: NodeIndex,
4929 builtin: struct {
4930 node: NodeIndex,
4931 tag: Builtin.Tag,
4932 },
4933
4934 fn init(p: *Parser, call_node: NodeIndex, func_node: NodeIndex) CallExpr {
4935 if (p.getNode(call_node, .builtin_call_expr_one)) |node| {
4936 const data = p.nodes.items(.data)[@intFromEnum(node)];
4937 const name = p.tokSlice(data.decl.name);
4938 const builtin_ty = p.comp.builtins.lookup(name);
4939 return .{ .builtin = .{ .node = node, .tag = builtin_ty.builtin.tag } };
4940 }
4941 return .{ .standard = func_node };
4942 }
4943
4944 fn shouldPerformLvalConversion(self: CallExpr, arg_idx: u32) bool {
4945 return switch (self) {
4946 .standard => true,
4947 .builtin => |builtin| switch (builtin.tag) {
4948 Builtin.tagFromName("__builtin_va_start").?,
4949 Builtin.tagFromName("__va_start").?,
4950 Builtin.tagFromName("va_start").?,
4951 => arg_idx != 1,
4952 else => true,
4953 },
4954 };
4955 }
4956
4957 fn shouldPromoteVarArg(self: CallExpr, arg_idx: u32) bool {
4958 return switch (self) {
4959 .standard => true,
4960 .builtin => |builtin| switch (builtin.tag) {
4961 Builtin.tagFromName("__builtin_va_start").?,
4962 Builtin.tagFromName("__va_start").?,
4963 Builtin.tagFromName("va_start").?,
4964 => arg_idx != 1,
4965 Builtin.tagFromName("__builtin_add_overflow").?,
4966 Builtin.tagFromName("__builtin_complex").?,
4967 Builtin.tagFromName("__builtin_isinf").?,
4968 Builtin.tagFromName("__builtin_isinf_sign").?,
4969 Builtin.tagFromName("__builtin_mul_overflow").?,
4970 Builtin.tagFromName("__builtin_isnan").?,
4971 Builtin.tagFromName("__builtin_sub_overflow").?,
4972 => false,
4973 else => true,
4974 },
4975 };
4976 }
4977
4978 fn shouldCoerceArg(self: CallExpr, arg_idx: u32) bool {
4979 _ = self;
4980 _ = arg_idx;
4981 return true;
4982 }
4983
4984 fn checkVarArg(self: CallExpr, p: *Parser, first_after: TokenIndex, param_tok: TokenIndex, arg: *Result, arg_idx: u32) !void {
4985 if (self == .standard) return;
4986
4987 const builtin_tok = p.nodes.items(.data)[@intFromEnum(self.builtin.node)].decl.name;
4988 switch (self.builtin.tag) {
4989 Builtin.tagFromName("__builtin_va_start").?,
4990 Builtin.tagFromName("__va_start").?,
4991 Builtin.tagFromName("va_start").?,
4992 => return p.checkVaStartArg(builtin_tok, first_after, param_tok, arg, arg_idx),
4993 Builtin.tagFromName("__builtin_complex").? => return p.checkComplexArg(builtin_tok, first_after, param_tok, arg, arg_idx),
4994 Builtin.tagFromName("__builtin_add_overflow").?,
4995 Builtin.tagFromName("__builtin_sub_overflow").?,
4996 Builtin.tagFromName("__builtin_mul_overflow").?,
4997 => return p.checkArithOverflowArg(builtin_tok, first_after, param_tok, arg, arg_idx),
4998
4999 else => {},
5000 }
5001 }
5002
5003 /// Some functions cannot be expressed as standard C prototypes. For example `__builtin_complex` requires
5004 /// two arguments of the same real floating point type (e.g. two doubles or two floats). These functions are
5005 /// encoded as varargs functions with custom typechecking. Since varargs functions do not have a fixed number
5006 /// of arguments, `paramCountOverride` is used to tell us how many arguments we should actually expect to see for
5007 /// these custom-typechecked functions.
5008 fn paramCountOverride(self: CallExpr) ?u32 {
5009 return switch (self) {
5010 .standard => null,
5011 .builtin => |builtin| switch (builtin.tag) {
5012 Builtin.tagFromName("__c11_atomic_thread_fence").?,
5013 Builtin.tagFromName("__c11_atomic_signal_fence").?,
5014 Builtin.tagFromName("__c11_atomic_is_lock_free").?,
5015 Builtin.tagFromName("__builtin_isinf").?,
5016 Builtin.tagFromName("__builtin_isinf_sign").?,
5017 Builtin.tagFromName("__builtin_isnan").?,
5018 => 1,
5019
5020 Builtin.tagFromName("__builtin_complex").?,
5021 Builtin.tagFromName("__c11_atomic_load").?,
5022 Builtin.tagFromName("__c11_atomic_init").?,
5023 => 2,
5024
5025 Builtin.tagFromName("__c11_atomic_store").?,
5026 Builtin.tagFromName("__c11_atomic_exchange").?,
5027 Builtin.tagFromName("__c11_atomic_fetch_add").?,
5028 Builtin.tagFromName("__c11_atomic_fetch_sub").?,
5029 Builtin.tagFromName("__c11_atomic_fetch_or").?,
5030 Builtin.tagFromName("__c11_atomic_fetch_xor").?,
5031 Builtin.tagFromName("__c11_atomic_fetch_and").?,
5032 Builtin.tagFromName("__atomic_fetch_add").?,
5033 Builtin.tagFromName("__atomic_fetch_sub").?,
5034 Builtin.tagFromName("__atomic_fetch_and").?,
5035 Builtin.tagFromName("__atomic_fetch_xor").?,
5036 Builtin.tagFromName("__atomic_fetch_or").?,
5037 Builtin.tagFromName("__atomic_fetch_nand").?,
5038 Builtin.tagFromName("__atomic_add_fetch").?,
5039 Builtin.tagFromName("__atomic_sub_fetch").?,
5040 Builtin.tagFromName("__atomic_and_fetch").?,
5041 Builtin.tagFromName("__atomic_xor_fetch").?,
5042 Builtin.tagFromName("__atomic_or_fetch").?,
5043 Builtin.tagFromName("__atomic_nand_fetch").?,
5044 Builtin.tagFromName("__builtin_add_overflow").?,
5045 Builtin.tagFromName("__builtin_sub_overflow").?,
5046 Builtin.tagFromName("__builtin_mul_overflow").?,
5047 => 3,
5048
5049 Builtin.tagFromName("__c11_atomic_compare_exchange_strong").?,
5050 Builtin.tagFromName("__c11_atomic_compare_exchange_weak").?,
5051 => 5,
5052
5053 Builtin.tagFromName("__atomic_compare_exchange").?,
5054 Builtin.tagFromName("__atomic_compare_exchange_n").?,
5055 => 6,
5056 else => null,
5057 },
5058 };
5059 }
5060
5061 fn returnType(self: CallExpr, p: *Parser, callable_ty: Type) Type {
5062 return switch (self) {
5063 .standard => callable_ty.returnType(),
5064 .builtin => |builtin| switch (builtin.tag) {
5065 Builtin.tagFromName("__c11_atomic_exchange").? => {
5066 if (p.list_buf.items.len != 4) return Type.invalid; // wrong number of arguments; already an error
5067 const second_param = p.list_buf.items[2];
5068 return p.nodes.items(.ty)[@intFromEnum(second_param)];
5069 },
5070 Builtin.tagFromName("__c11_atomic_load").? => {
5071 if (p.list_buf.items.len != 3) return Type.invalid; // wrong number of arguments; already an error
5072 const first_param = p.list_buf.items[1];
5073 const ty = p.nodes.items(.ty)[@intFromEnum(first_param)];
5074 if (!ty.isPtr()) return Type.invalid;
5075 return ty.elemType();
5076 },
5077
5078 Builtin.tagFromName("__atomic_fetch_add").?,
5079 Builtin.tagFromName("__atomic_add_fetch").?,
5080 Builtin.tagFromName("__c11_atomic_fetch_add").?,
5081
5082 Builtin.tagFromName("__atomic_fetch_sub").?,
5083 Builtin.tagFromName("__atomic_sub_fetch").?,
5084 Builtin.tagFromName("__c11_atomic_fetch_sub").?,
5085
5086 Builtin.tagFromName("__atomic_fetch_and").?,
5087 Builtin.tagFromName("__atomic_and_fetch").?,
5088 Builtin.tagFromName("__c11_atomic_fetch_and").?,
5089
5090 Builtin.tagFromName("__atomic_fetch_xor").?,
5091 Builtin.tagFromName("__atomic_xor_fetch").?,
5092 Builtin.tagFromName("__c11_atomic_fetch_xor").?,
5093
5094 Builtin.tagFromName("__atomic_fetch_or").?,
5095 Builtin.tagFromName("__atomic_or_fetch").?,
5096 Builtin.tagFromName("__c11_atomic_fetch_or").?,
5097
5098 Builtin.tagFromName("__atomic_fetch_nand").?,
5099 Builtin.tagFromName("__atomic_nand_fetch").?,
5100 Builtin.tagFromName("__c11_atomic_fetch_nand").?,
5101 => {
5102 if (p.list_buf.items.len != 3) return Type.invalid; // wrong number of arguments; already an error
5103 const second_param = p.list_buf.items[2];
5104 return p.nodes.items(.ty)[@intFromEnum(second_param)];
5105 },
5106 Builtin.tagFromName("__builtin_complex").? => {
5107 if (p.list_buf.items.len < 1) return Type.invalid; // not enough arguments; already an error
5108 const last_param = p.list_buf.items[p.list_buf.items.len - 1];
5109 return p.nodes.items(.ty)[@intFromEnum(last_param)].makeComplex();
5110 },
5111 Builtin.tagFromName("__atomic_compare_exchange").?,
5112 Builtin.tagFromName("__atomic_compare_exchange_n").?,
5113 Builtin.tagFromName("__c11_atomic_is_lock_free").?,
5114 => .{ .specifier = .bool },
5115 else => callable_ty.returnType(),
5116
5117 Builtin.tagFromName("__c11_atomic_compare_exchange_strong").?,
5118 Builtin.tagFromName("__c11_atomic_compare_exchange_weak").?,
5119 => {
5120 if (p.list_buf.items.len != 6) return Type.invalid; // wrong number of arguments
5121 const third_param = p.list_buf.items[3];
5122 return p.nodes.items(.ty)[@intFromEnum(third_param)];
5123 },
5124 },
5125 };
5126 }
5127
5128 fn finish(self: CallExpr, p: *Parser, ty: Type, list_buf_top: usize, arg_count: u32) Error!Result {
5129 const ret_ty = self.returnType(p, ty);
5130 switch (self) {
5131 .standard => |func_node| {
5132 var call_node: Tree.Node = .{
5133 .tag = .call_expr_one,
5134 .ty = ret_ty,
5135 .data = .{ .two = .{ func_node, .none } },
5136 };
5137 const args = p.list_buf.items[list_buf_top..];
5138 switch (arg_count) {
5139 0 => {},
5140 1 => call_node.data.two[1] = args[1], // args[0] == func.node
5141 else => {
5142 call_node.tag = .call_expr;
5143 call_node.data = .{ .range = try p.addList(args) };
5144 },
5145 }
5146 return Result{ .node = try p.addNode(call_node), .ty = ret_ty };
5147 },
5148 .builtin => |builtin| {
5149 const index = @intFromEnum(builtin.node);
5150 var call_node = p.nodes.get(index);
5151 defer p.nodes.set(index, call_node);
5152 call_node.ty = ret_ty;
5153 const args = p.list_buf.items[list_buf_top..];
5154 switch (arg_count) {
5155 0 => {},
5156 1 => call_node.data.decl.node = args[1], // args[0] == func.node
5157 else => {
5158 call_node.tag = .builtin_call_expr;
5159 args[0] = @enumFromInt(call_node.data.decl.name);
5160 call_node.data = .{ .range = try p.addList(args) };
5161 },
5162 }
5163 const val = try evalBuiltin(builtin.tag, p, args[1..]);
5164 return Result{ .node = builtin.node, .ty = ret_ty, .val = val };
5165 },
5166 }
5167 }
5168};
5169
5170pub const Result = struct {
5171 node: NodeIndex = .none,
5172 ty: Type = .{ .specifier = .int },
5173 val: Value = .{},
5174
5175 const invalid: Result = .{ .ty = Type.invalid };
5176
5177 pub fn str(res: Result, p: *Parser) ![]const u8 {
5178 switch (res.val.opt_ref) {
5179 .none => return "(none)",
5180 .null => return "nullptr_t",
5181 else => {},
5182 }
5183 const strings_top = p.strings.items.len;
5184 defer p.strings.items.len = strings_top;
5185
5186 try res.val.print(res.ty, p.comp, p.strings.writer());
5187 return try p.comp.diagnostics.arena.allocator().dupe(u8, p.strings.items[strings_top..]);
5188 }
5189
5190 fn expect(res: Result, p: *Parser) Error!void {
5191 if (p.in_macro) {
5192 if (res.val.opt_ref == .none) {
5193 try p.errTok(.expected_expr, p.tok_i);
5194 return error.ParsingFailed;
5195 }
5196 return;
5197 }
5198 if (res.node == .none) {
5199 try p.errTok(.expected_expr, p.tok_i);
5200 return error.ParsingFailed;
5201 }
5202 }
5203
5204 fn empty(res: Result, p: *Parser) bool {
5205 if (p.in_macro) return res.val.opt_ref == .none;
5206 return res.node == .none;
5207 }
5208
5209 fn maybeWarnUnused(res: Result, p: *Parser, expr_start: TokenIndex, err_start: usize) Error!void {
5210 if (res.ty.is(.void) or res.node == .none) return;
5211 // don't warn about unused result if the expression contained errors besides other unused results
5212 for (p.comp.diagnostics.list.items[err_start..]) |err_item| {
5213 if (err_item.tag != .unused_value) return;
5214 }
5215 var cur_node = res.node;
5216 while (true) switch (p.nodes.items(.tag)[@intFromEnum(cur_node)]) {
5217 .invalid, // So that we don't need to check for node == 0
5218 .assign_expr,
5219 .mul_assign_expr,
5220 .div_assign_expr,
5221 .mod_assign_expr,
5222 .add_assign_expr,
5223 .sub_assign_expr,
5224 .shl_assign_expr,
5225 .shr_assign_expr,
5226 .bit_and_assign_expr,
5227 .bit_xor_assign_expr,
5228 .bit_or_assign_expr,
5229 .pre_inc_expr,
5230 .pre_dec_expr,
5231 .post_inc_expr,
5232 .post_dec_expr,
5233 => return,
5234 .call_expr, .call_expr_one => {
5235 const tmp_tree = p.tmpTree();
5236 const child_nodes = tmp_tree.childNodes(cur_node);
5237 const fn_ptr = child_nodes[0];
5238 const call_info = tmp_tree.callableResultUsage(fn_ptr) orelse return;
5239 if (call_info.nodiscard) try p.errStr(.nodiscard_unused, expr_start, p.tokSlice(call_info.tok));
5240 if (call_info.warn_unused_result) try p.errStr(.warn_unused_result, expr_start, p.tokSlice(call_info.tok));
5241 return;
5242 },
5243 .stmt_expr => {
5244 const body = p.nodes.items(.data)[@intFromEnum(cur_node)].un;
5245 switch (p.nodes.items(.tag)[@intFromEnum(body)]) {
5246 .compound_stmt_two => {
5247 const body_stmt = p.nodes.items(.data)[@intFromEnum(body)].two;
5248 cur_node = if (body_stmt[1] != .none) body_stmt[1] else body_stmt[0];
5249 },
5250 .compound_stmt => {
5251 const data = p.nodes.items(.data)[@intFromEnum(body)];
5252 cur_node = p.data.items[data.range.end - 1];
5253 },
5254 else => unreachable,
5255 }
5256 },
5257 .comma_expr => cur_node = p.nodes.items(.data)[@intFromEnum(cur_node)].bin.rhs,
5258 .paren_expr => cur_node = p.nodes.items(.data)[@intFromEnum(cur_node)].un,
5259 else => break,
5260 };
5261 try p.errTok(.unused_value, expr_start);
5262 }
5263
5264 fn boolRes(lhs: *Result, p: *Parser, tag: Tree.Tag, rhs: Result, tok_i: TokenIndex) !void {
5265 if (lhs.val.opt_ref == .null) {
5266 lhs.val = Value.zero;
5267 }
5268 if (lhs.ty.specifier != .invalid) {
5269 lhs.ty = Type.int;
5270 }
5271 return lhs.bin(p, tag, rhs, tok_i);
5272 }
5273
5274 fn bin(lhs: *Result, p: *Parser, tag: Tree.Tag, rhs: Result, tok_i: TokenIndex) !void {
5275 lhs.node = try p.addNode(.{
5276 .tag = tag,
5277 .ty = lhs.ty,
5278 .data = .{ .bin = .{ .lhs = lhs.node, .rhs = rhs.node } },
5279 .loc = @enumFromInt(tok_i),
5280 });
5281 }
5282
5283 fn un(operand: *Result, p: *Parser, tag: Tree.Tag, tok_i: TokenIndex) Error!void {
5284 operand.node = try p.addNode(.{
5285 .tag = tag,
5286 .ty = operand.ty,
5287 .data = .{ .un = operand.node },
5288 .loc = @enumFromInt(tok_i),
5289 });
5290 }
5291
5292 fn implicitCast(operand: *Result, p: *Parser, kind: Tree.CastKind) Error!void {
5293 operand.node = try p.addNode(.{
5294 .tag = .implicit_cast,
5295 .ty = operand.ty,
5296 .data = .{ .cast = .{ .operand = operand.node, .kind = kind } },
5297 });
5298 }
5299
5300 fn adjustCondExprPtrs(a: *Result, tok: TokenIndex, b: *Result, p: *Parser) !bool {
5301 assert(a.ty.isPtr() and b.ty.isPtr());
5302
5303 const a_elem = a.ty.elemType();
5304 const b_elem = b.ty.elemType();
5305 if (a_elem.eql(b_elem, p.comp, true)) return true;
5306
5307 var adjusted_elem_ty = try p.arena.create(Type);
5308 adjusted_elem_ty.* = a_elem;
5309
5310 const has_void_star_branch = a.ty.isVoidStar() or b.ty.isVoidStar();
5311 const only_quals_differ = a_elem.eql(b_elem, p.comp, false);
5312 const pointers_compatible = only_quals_differ or has_void_star_branch;
5313
5314 if (!pointers_compatible or has_void_star_branch) {
5315 if (!pointers_compatible) {
5316 try p.errStr(.pointer_mismatch, tok, try p.typePairStrExtra(a.ty, " and ", b.ty));
5317 }
5318 adjusted_elem_ty.* = .{ .specifier = .void };
5319 }
5320 if (pointers_compatible) {
5321 adjusted_elem_ty.qual = a_elem.qual.mergeCV(b_elem.qual);
5322 }
5323 if (!adjusted_elem_ty.eql(a_elem, p.comp, true)) {
5324 a.ty = .{
5325 .data = .{ .sub_type = adjusted_elem_ty },
5326 .specifier = .pointer,
5327 };
5328 try a.implicitCast(p, .bitcast);
5329 }
5330 if (!adjusted_elem_ty.eql(b_elem, p.comp, true)) {
5331 b.ty = .{
5332 .data = .{ .sub_type = adjusted_elem_ty },
5333 .specifier = .pointer,
5334 };
5335 try b.implicitCast(p, .bitcast);
5336 }
5337 return true;
5338 }
5339
5340 /// Adjust types for binary operation, returns true if the result can and should be evaluated.
5341 fn adjustTypes(a: *Result, tok: TokenIndex, b: *Result, p: *Parser, kind: enum {
5342 integer,
5343 arithmetic,
5344 boolean_logic,
5345 relational,
5346 equality,
5347 conditional,
5348 add,
5349 sub,
5350 }) !bool {
5351 if (b.ty.specifier == .invalid) {
5352 try a.saveValue(p);
5353 a.ty = Type.invalid;
5354 }
5355 if (a.ty.specifier == .invalid) {
5356 return false;
5357 }
5358 try a.lvalConversion(p);
5359 try b.lvalConversion(p);
5360
5361 const a_vec = a.ty.is(.vector);
5362 const b_vec = b.ty.is(.vector);
5363 if (a_vec and b_vec) {
5364 if (a.ty.eql(b.ty, p.comp, false)) {
5365 return a.shouldEval(b, p);
5366 }
5367 return a.invalidBinTy(tok, b, p);
5368 } else if (a_vec) {
5369 if (b.coerceExtra(p, a.ty.elemType(), tok, .test_coerce)) {
5370 try b.saveValue(p);
5371 try b.implicitCast(p, .vector_splat);
5372 return a.shouldEval(b, p);
5373 } else |er| switch (er) {
5374 error.CoercionFailed => return a.invalidBinTy(tok, b, p),
5375 else => |e| return e,
5376 }
5377 } else if (b_vec) {
5378 if (a.coerceExtra(p, b.ty.elemType(), tok, .test_coerce)) {
5379 try a.saveValue(p);
5380 try a.implicitCast(p, .vector_splat);
5381 return a.shouldEval(b, p);
5382 } else |er| switch (er) {
5383 error.CoercionFailed => return a.invalidBinTy(tok, b, p),
5384 else => |e| return e,
5385 }
5386 }
5387
5388 const a_int = a.ty.isInt();
5389 const b_int = b.ty.isInt();
5390 if (a_int and b_int) {
5391 try a.usualArithmeticConversion(b, p, tok);
5392 return a.shouldEval(b, p);
5393 }
5394 if (kind == .integer) return a.invalidBinTy(tok, b, p);
5395
5396 const a_float = a.ty.isFloat();
5397 const b_float = b.ty.isFloat();
5398 const a_arithmetic = a_int or a_float;
5399 const b_arithmetic = b_int or b_float;
5400 if (a_arithmetic and b_arithmetic) {
5401 // <, <=, >, >= only work on real types
5402 if (kind == .relational and (!a.ty.isReal() or !b.ty.isReal()))
5403 return a.invalidBinTy(tok, b, p);
5404
5405 try a.usualArithmeticConversion(b, p, tok);
5406 return a.shouldEval(b, p);
5407 }
5408 if (kind == .arithmetic) return a.invalidBinTy(tok, b, p);
5409
5410 const a_nullptr = a.ty.is(.nullptr_t);
5411 const b_nullptr = b.ty.is(.nullptr_t);
5412 const a_ptr = a.ty.isPtr();
5413 const b_ptr = b.ty.isPtr();
5414 const a_scalar = a_arithmetic or a_ptr;
5415 const b_scalar = b_arithmetic or b_ptr;
5416 switch (kind) {
5417 .boolean_logic => {
5418 if (!(a_scalar or a_nullptr) or !(b_scalar or b_nullptr)) return a.invalidBinTy(tok, b, p);
5419
5420 // Do integer promotions but nothing else
5421 if (a_int) try a.intCast(p, a.ty.integerPromotion(p.comp), tok);
5422 if (b_int) try b.intCast(p, b.ty.integerPromotion(p.comp), tok);
5423 return a.shouldEval(b, p);
5424 },
5425 .relational, .equality => {
5426 if (kind == .equality and (a_nullptr or b_nullptr)) {
5427 if (a_nullptr and b_nullptr) return a.shouldEval(b, p);
5428 const nullptr_res = if (a_nullptr) a else b;
5429 const other_res = if (a_nullptr) b else a;
5430 if (other_res.ty.isPtr()) {
5431 try nullptr_res.nullCast(p, other_res.ty);
5432 return other_res.shouldEval(nullptr_res, p);
5433 } else if (other_res.val.isZero(p.comp)) {
5434 other_res.val = Value.null;
5435 try other_res.nullCast(p, nullptr_res.ty);
5436 return other_res.shouldEval(nullptr_res, p);
5437 }
5438 return a.invalidBinTy(tok, b, p);
5439 }
5440 // comparisons between floats and pointes not allowed
5441 if (!a_scalar or !b_scalar or (a_float and b_ptr) or (b_float and a_ptr))
5442 return a.invalidBinTy(tok, b, p);
5443
5444 if ((a_int or b_int) and !(a.val.isZero(p.comp) or b.val.isZero(p.comp))) {
5445 try p.errStr(.comparison_ptr_int, tok, try p.typePairStr(a.ty, b.ty));
5446 } else if (a_ptr and b_ptr) {
5447 if (!a.ty.isVoidStar() and !b.ty.isVoidStar() and !a.ty.eql(b.ty, p.comp, false))
5448 try p.errStr(.comparison_distinct_ptr, tok, try p.typePairStr(a.ty, b.ty));
5449 } else if (a_ptr) {
5450 try b.ptrCast(p, a.ty);
5451 } else {
5452 assert(b_ptr);
5453 try a.ptrCast(p, b.ty);
5454 }
5455
5456 return a.shouldEval(b, p);
5457 },
5458 .conditional => {
5459 // doesn't matter what we return here, as the result is ignored
5460 if (a.ty.is(.void) or b.ty.is(.void)) {
5461 try a.toVoid(p);
5462 try b.toVoid(p);
5463 return true;
5464 }
5465 if (a_nullptr and b_nullptr) return true;
5466 if ((a_ptr and b_int) or (a_int and b_ptr)) {
5467 if (a.val.isZero(p.comp) or b.val.isZero(p.comp)) {
5468 try a.nullCast(p, b.ty);
5469 try b.nullCast(p, a.ty);
5470 return true;
5471 }
5472 const int_ty = if (a_int) a else b;
5473 const ptr_ty = if (a_ptr) a else b;
5474 try p.errStr(.implicit_int_to_ptr, tok, try p.typePairStrExtra(int_ty.ty, " to ", ptr_ty.ty));
5475 try int_ty.ptrCast(p, ptr_ty.ty);
5476
5477 return true;
5478 }
5479 if (a_ptr and b_ptr) return a.adjustCondExprPtrs(tok, b, p);
5480 if ((a_ptr and b_nullptr) or (a_nullptr and b_ptr)) {
5481 const nullptr_res = if (a_nullptr) a else b;
5482 const ptr_res = if (a_nullptr) b else a;
5483 try nullptr_res.nullCast(p, ptr_res.ty);
5484 return true;
5485 }
5486 if (a.ty.isRecord() and b.ty.isRecord() and a.ty.eql(b.ty, p.comp, false)) {
5487 return true;
5488 }
5489 return a.invalidBinTy(tok, b, p);
5490 },
5491 .add => {
5492 // if both aren't arithmetic one should be pointer and the other an integer
5493 if (a_ptr == b_ptr or a_int == b_int) return a.invalidBinTy(tok, b, p);
5494
5495 // Do integer promotions but nothing else
5496 if (a_int) try a.intCast(p, a.ty.integerPromotion(p.comp), tok);
5497 if (b_int) try b.intCast(p, b.ty.integerPromotion(p.comp), tok);
5498
5499 // The result type is the type of the pointer operand
5500 if (a_int) a.ty = b.ty else b.ty = a.ty;
5501 return a.shouldEval(b, p);
5502 },
5503 .sub => {
5504 // if both aren't arithmetic then either both should be pointers or just a
5505 if (!a_ptr or !(b_ptr or b_int)) return a.invalidBinTy(tok, b, p);
5506
5507 if (a_ptr and b_ptr) {
5508 if (!a.ty.eql(b.ty, p.comp, false)) try p.errStr(.incompatible_pointers, tok, try p.typePairStr(a.ty, b.ty));
5509 a.ty = p.comp.types.ptrdiff;
5510 }
5511
5512 // Do integer promotion on b if needed
5513 if (b_int) try b.intCast(p, b.ty.integerPromotion(p.comp), tok);
5514 return a.shouldEval(b, p);
5515 },
5516 else => return a.invalidBinTy(tok, b, p),
5517 }
5518 }
5519
5520 fn lvalConversion(res: *Result, p: *Parser) Error!void {
5521 if (res.ty.isFunc()) {
5522 if (res.ty.isInvalidFunc()) {
5523 res.ty = .{ .specifier = .invalid };
5524 } else {
5525 const elem_ty = try p.arena.create(Type);
5526 elem_ty.* = res.ty;
5527 res.ty.specifier = .pointer;
5528 res.ty.data = .{ .sub_type = elem_ty };
5529 }
5530 try res.implicitCast(p, .function_to_pointer);
5531 } else if (res.ty.isArray()) {
5532 res.val = .{};
5533 res.ty.decayArray();
5534 try res.implicitCast(p, .array_to_pointer);
5535 } else if (!p.in_macro and p.tmpTree().isLval(res.node)) {
5536 res.ty.qual = .{};
5537 try res.implicitCast(p, .lval_to_rval);
5538 }
5539 }
5540
5541 fn boolCast(res: *Result, p: *Parser, bool_ty: Type, tok: TokenIndex) Error!void {
5542 if (res.ty.isArray()) {
5543 if (res.val.is(.bytes, p.comp)) {
5544 try p.errStr(.string_literal_to_bool, tok, try p.typePairStrExtra(res.ty, " to ", bool_ty));
5545 } else {
5546 try p.errStr(.array_address_to_bool, tok, p.tokSlice(tok));
5547 }
5548 try res.lvalConversion(p);
5549 res.val = Value.one;
5550 res.ty = bool_ty;
5551 try res.implicitCast(p, .pointer_to_bool);
5552 } else if (res.ty.isPtr()) {
5553 res.val.boolCast(p.comp);
5554 res.ty = bool_ty;
5555 try res.implicitCast(p, .pointer_to_bool);
5556 } else if (res.ty.isInt() and !res.ty.is(.bool)) {
5557 res.val.boolCast(p.comp);
5558 res.ty = bool_ty;
5559 try res.implicitCast(p, .int_to_bool);
5560 } else if (res.ty.isFloat()) {
5561 const old_value = res.val;
5562 const value_change_kind = try res.val.floatToInt(bool_ty, p.comp);
5563 try res.floatToIntWarning(p, bool_ty, old_value, value_change_kind, tok);
5564 if (!res.ty.isReal()) {
5565 res.ty = res.ty.makeReal();
5566 try res.implicitCast(p, .complex_float_to_real);
5567 }
5568 res.ty = bool_ty;
5569 try res.implicitCast(p, .float_to_bool);
5570 }
5571 }
5572
5573 fn intCast(res: *Result, p: *Parser, int_ty: Type, tok: TokenIndex) Error!void {
5574 if (int_ty.hasIncompleteSize()) return error.ParsingFailed; // Diagnostic already issued
5575 if (res.ty.is(.bool)) {
5576 res.ty = int_ty.makeReal();
5577 try res.implicitCast(p, .bool_to_int);
5578 if (!int_ty.isReal()) {
5579 res.ty = int_ty;
5580 try res.implicitCast(p, .real_to_complex_int);
5581 }
5582 } else if (res.ty.isPtr()) {
5583 res.ty = int_ty.makeReal();
5584 try res.implicitCast(p, .pointer_to_int);
5585 if (!int_ty.isReal()) {
5586 res.ty = int_ty;
5587 try res.implicitCast(p, .real_to_complex_int);
5588 }
5589 } else if (res.ty.isFloat()) {
5590 const old_value = res.val;
5591 const value_change_kind = try res.val.floatToInt(int_ty, p.comp);
5592 try res.floatToIntWarning(p, int_ty, old_value, value_change_kind, tok);
5593 const old_real = res.ty.isReal();
5594 const new_real = int_ty.isReal();
5595 if (old_real and new_real) {
5596 res.ty = int_ty;
5597 try res.implicitCast(p, .float_to_int);
5598 } else if (old_real) {
5599 res.ty = int_ty.makeReal();
5600 try res.implicitCast(p, .float_to_int);
5601 res.ty = int_ty;
5602 try res.implicitCast(p, .real_to_complex_int);
5603 } else if (new_real) {
5604 res.ty = res.ty.makeReal();
5605 try res.implicitCast(p, .complex_float_to_real);
5606 res.ty = int_ty;
5607 try res.implicitCast(p, .float_to_int);
5608 } else {
5609 res.ty = int_ty;
5610 try res.implicitCast(p, .complex_float_to_complex_int);
5611 }
5612 } else if (!res.ty.eql(int_ty, p.comp, true)) {
5613 const old_val = res.val;
5614 const value_change_kind = try res.val.intCast(int_ty, p.comp);
5615 switch (value_change_kind) {
5616 .none => {},
5617 .truncated => try p.errStr(.int_value_changed, tok, try p.valueChangedStr(res, old_val, int_ty)),
5618 .sign_changed => try p.errStr(.sign_conversion, tok, try p.typePairStrExtra(res.ty, " to ", int_ty)),
5619 }
5620
5621 const old_real = res.ty.isReal();
5622 const new_real = int_ty.isReal();
5623 if (old_real and new_real) {
5624 res.ty = int_ty;
5625 try res.implicitCast(p, .int_cast);
5626 } else if (old_real) {
5627 const real_int_ty = int_ty.makeReal();
5628 if (!res.ty.eql(real_int_ty, p.comp, false)) {
5629 res.ty = real_int_ty;
5630 try res.implicitCast(p, .int_cast);
5631 }
5632 res.ty = int_ty;
5633 try res.implicitCast(p, .real_to_complex_int);
5634 } else if (new_real) {
5635 res.ty = res.ty.makeReal();
5636 try res.implicitCast(p, .complex_int_to_real);
5637 res.ty = int_ty;
5638 try res.implicitCast(p, .int_cast);
5639 } else {
5640 res.ty = int_ty;
5641 try res.implicitCast(p, .complex_int_cast);
5642 }
5643 }
5644 }
5645
5646 fn floatToIntWarning(res: *Result, p: *Parser, int_ty: Type, old_value: Value, change_kind: Value.FloatToIntChangeKind, tok: TokenIndex) !void {
5647 switch (change_kind) {
5648 .none => return p.errStr(.float_to_int, tok, try p.typePairStrExtra(res.ty, " to ", int_ty)),
5649 .out_of_range => return p.errStr(.float_out_of_range, tok, try p.typePairStrExtra(res.ty, " to ", int_ty)),
5650 .overflow => return p.errStr(.float_overflow_conversion, tok, try p.typePairStrExtra(res.ty, " to ", int_ty)),
5651 .nonzero_to_zero => return p.errStr(.float_zero_conversion, tok, try p.valueChangedStr(res, old_value, int_ty)),
5652 .value_changed => return p.errStr(.float_value_changed, tok, try p.valueChangedStr(res, old_value, int_ty)),
5653 }
5654 }
5655
5656 fn floatCast(res: *Result, p: *Parser, float_ty: Type) Error!void {
5657 if (res.ty.is(.bool)) {
5658 try res.val.intToFloat(float_ty, p.comp);
5659 res.ty = float_ty.makeReal();
5660 try res.implicitCast(p, .bool_to_float);
5661 if (!float_ty.isReal()) {
5662 res.ty = float_ty;
5663 try res.implicitCast(p, .real_to_complex_float);
5664 }
5665 } else if (res.ty.isInt()) {
5666 try res.val.intToFloat(float_ty, p.comp);
5667 const old_real = res.ty.isReal();
5668 const new_real = float_ty.isReal();
5669 if (old_real and new_real) {
5670 res.ty = float_ty;
5671 try res.implicitCast(p, .int_to_float);
5672 } else if (old_real) {
5673 res.ty = float_ty.makeReal();
5674 try res.implicitCast(p, .int_to_float);
5675 res.ty = float_ty;
5676 try res.implicitCast(p, .real_to_complex_float);
5677 } else if (new_real) {
5678 res.ty = res.ty.makeReal();
5679 try res.implicitCast(p, .complex_int_to_real);
5680 res.ty = float_ty;
5681 try res.implicitCast(p, .int_to_float);
5682 } else {
5683 res.ty = float_ty;
5684 try res.implicitCast(p, .complex_int_to_complex_float);
5685 }
5686 } else if (!res.ty.eql(float_ty, p.comp, true)) {
5687 try res.val.floatCast(float_ty, p.comp);
5688 const old_real = res.ty.isReal();
5689 const new_real = float_ty.isReal();
5690 if (old_real and new_real) {
5691 res.ty = float_ty;
5692 try res.implicitCast(p, .float_cast);
5693 } else if (old_real) {
5694 if (res.ty.floatRank() != float_ty.floatRank()) {
5695 res.ty = float_ty.makeReal();
5696 try res.implicitCast(p, .float_cast);
5697 }
5698 res.ty = float_ty;
5699 try res.implicitCast(p, .real_to_complex_float);
5700 } else if (new_real) {
5701 res.ty = res.ty.makeReal();
5702 try res.implicitCast(p, .complex_float_to_real);
5703 if (res.ty.floatRank() != float_ty.floatRank()) {
5704 res.ty = float_ty;
5705 try res.implicitCast(p, .float_cast);
5706 }
5707 } else {
5708 res.ty = float_ty;
5709 try res.implicitCast(p, .complex_float_cast);
5710 }
5711 }
5712 }
5713
5714 /// Converts a bool or integer to a pointer
5715 fn ptrCast(res: *Result, p: *Parser, ptr_ty: Type) Error!void {
5716 if (res.ty.is(.bool)) {
5717 res.ty = ptr_ty;
5718 try res.implicitCast(p, .bool_to_pointer);
5719 } else if (res.ty.isInt()) {
5720 _ = try res.val.intCast(ptr_ty, p.comp);
5721 res.ty = ptr_ty;
5722 try res.implicitCast(p, .int_to_pointer);
5723 }
5724 }
5725
5726 /// Convert pointer to one with a different child type
5727 fn ptrChildTypeCast(res: *Result, p: *Parser, ptr_ty: Type) Error!void {
5728 res.ty = ptr_ty;
5729 return res.implicitCast(p, .bitcast);
5730 }
5731
5732 fn toVoid(res: *Result, p: *Parser) Error!void {
5733 if (!res.ty.is(.void)) {
5734 res.ty = .{ .specifier = .void };
5735 try res.implicitCast(p, .to_void);
5736 }
5737 }
5738
5739 fn nullCast(res: *Result, p: *Parser, ptr_ty: Type) Error!void {
5740 if (!res.ty.is(.nullptr_t) and !res.val.isZero(p.comp)) return;
5741 res.ty = ptr_ty;
5742 try res.implicitCast(p, .null_to_pointer);
5743 }
5744
5745 fn usualUnaryConversion(res: *Result, p: *Parser, tok: TokenIndex) Error!void {
5746 if (res.ty.isFloat()) fp_eval: {
5747 const eval_method = p.comp.langopts.fp_eval_method orelse break :fp_eval;
5748 switch (eval_method) {
5749 .source => {},
5750 .indeterminate => unreachable,
5751 .double => {
5752 if (res.ty.floatRank() < (Type{ .specifier = .double }).floatRank()) {
5753 const spec: Type.Specifier = if (res.ty.isReal()) .double else .complex_double;
5754 return res.floatCast(p, .{ .specifier = spec });
5755 }
5756 },
5757 .extended => {
5758 if (res.ty.floatRank() < (Type{ .specifier = .long_double }).floatRank()) {
5759 const spec: Type.Specifier = if (res.ty.isReal()) .long_double else .complex_long_double;
5760 return res.floatCast(p, .{ .specifier = spec });
5761 }
5762 },
5763 }
5764 }
5765
5766 if (res.ty.is(.fp16) and !p.comp.langopts.use_native_half_type) {
5767 return res.floatCast(p, .{ .specifier = .float });
5768 }
5769 if (res.ty.isInt()) {
5770 if (p.tmpTree().bitfieldWidth(res.node, true)) |width| {
5771 if (res.ty.bitfieldPromotion(p.comp, width)) |promotion_ty| {
5772 return res.intCast(p, promotion_ty, tok);
5773 }
5774 }
5775 return res.intCast(p, res.ty.integerPromotion(p.comp), tok);
5776 }
5777 }
5778
5779 fn usualArithmeticConversion(a: *Result, b: *Result, p: *Parser, tok: TokenIndex) Error!void {
5780 try a.usualUnaryConversion(p, tok);
5781 try b.usualUnaryConversion(p, tok);
5782
5783 // if either is a float cast to that type
5784 if (a.ty.isFloat() or b.ty.isFloat()) {
5785 const float_types = [6][2]Type.Specifier{
5786 .{ .complex_long_double, .long_double },
5787 .{ .complex_float128, .float128 },
5788 .{ .complex_double, .double },
5789 .{ .complex_float, .float },
5790 // No `_Complex __fp16` type
5791 .{ .invalid, .fp16 },
5792 .{ .complex_float16, .float16 },
5793 };
5794 const a_spec = a.ty.canonicalize(.standard).specifier;
5795 const b_spec = b.ty.canonicalize(.standard).specifier;
5796 if (p.comp.target.cTypeBitSize(.longdouble) == 128) {
5797 if (try a.floatConversion(b, a_spec, b_spec, p, float_types[0])) return;
5798 }
5799 if (try a.floatConversion(b, a_spec, b_spec, p, float_types[1])) return;
5800 if (p.comp.target.cTypeBitSize(.longdouble) == 80) {
5801 if (try a.floatConversion(b, a_spec, b_spec, p, float_types[0])) return;
5802 }
5803 if (try a.floatConversion(b, a_spec, b_spec, p, float_types[2])) return;
5804 if (p.comp.target.cTypeBitSize(.longdouble) == 64) {
5805 if (try a.floatConversion(b, a_spec, b_spec, p, float_types[0])) return;
5806 }
5807 if (try a.floatConversion(b, a_spec, b_spec, p, float_types[3])) return;
5808 if (try a.floatConversion(b, a_spec, b_spec, p, float_types[4])) return;
5809 if (try a.floatConversion(b, a_spec, b_spec, p, float_types[5])) return;
5810 unreachable;
5811 }
5812
5813 if (a.ty.eql(b.ty, p.comp, true)) {
5814 // cast to promoted type
5815 try a.intCast(p, a.ty, tok);
5816 try b.intCast(p, b.ty, tok);
5817 return;
5818 }
5819
5820 const target = a.ty.integerConversion(b.ty, p.comp);
5821 if (!target.isReal()) {
5822 try a.saveValue(p);
5823 try b.saveValue(p);
5824 }
5825 try a.intCast(p, target, tok);
5826 try b.intCast(p, target, tok);
5827 }
5828
5829 fn floatConversion(a: *Result, b: *Result, a_spec: Type.Specifier, b_spec: Type.Specifier, p: *Parser, pair: [2]Type.Specifier) !bool {
5830 if (a_spec == pair[0] or a_spec == pair[1] or
5831 b_spec == pair[0] or b_spec == pair[1])
5832 {
5833 const both_real = a.ty.isReal() and b.ty.isReal();
5834 const res_spec = pair[@intFromBool(both_real)];
5835 const ty = Type{ .specifier = res_spec };
5836 try a.floatCast(p, ty);
5837 try b.floatCast(p, ty);
5838 return true;
5839 }
5840 return false;
5841 }
5842
5843 fn invalidBinTy(a: *Result, tok: TokenIndex, b: *Result, p: *Parser) Error!bool {
5844 try p.errStr(.invalid_bin_types, tok, try p.typePairStr(a.ty, b.ty));
5845 a.val = .{};
5846 b.val = .{};
5847 a.ty = Type.invalid;
5848 return false;
5849 }
5850
5851 fn shouldEval(a: *Result, b: *Result, p: *Parser) Error!bool {
5852 if (p.no_eval) return false;
5853 if (a.val.opt_ref != .none and b.val.opt_ref != .none)
5854 return true;
5855
5856 try a.saveValue(p);
5857 try b.saveValue(p);
5858 return p.no_eval;
5859 }
5860
5861 /// Saves value and replaces it with `.unavailable`.
5862 fn saveValue(res: *Result, p: *Parser) !void {
5863 assert(!p.in_macro);
5864 if (res.val.opt_ref == .none or res.val.opt_ref == .null) return;
5865 if (!p.in_macro) try p.value_map.put(res.node, res.val);
5866 res.val = .{};
5867 }
5868
5869 fn castType(res: *Result, p: *Parser, to: Type, operand_tok: TokenIndex, l_paren: TokenIndex) !void {
5870 var cast_kind: Tree.CastKind = undefined;
5871
5872 if (to.is(.void)) {
5873 // everything can cast to void
5874 cast_kind = .to_void;
5875 res.val = .{};
5876 } else if (to.is(.nullptr_t)) {
5877 if (res.ty.is(.nullptr_t)) {
5878 cast_kind = .no_op;
5879 } else {
5880 try p.errStr(.invalid_object_cast, l_paren, try p.typePairStrExtra(res.ty, " to ", to));
5881 return error.ParsingFailed;
5882 }
5883 } else if (res.ty.is(.nullptr_t)) {
5884 if (to.is(.bool)) {
5885 try res.nullCast(p, res.ty);
5886 res.val.boolCast(p.comp);
5887 res.ty = .{ .specifier = .bool };
5888 try res.implicitCast(p, .pointer_to_bool);
5889 try res.saveValue(p);
5890 } else if (to.isPtr()) {
5891 try res.nullCast(p, to);
5892 } else {
5893 try p.errStr(.invalid_object_cast, l_paren, try p.typePairStrExtra(res.ty, " to ", to));
5894 return error.ParsingFailed;
5895 }
5896 cast_kind = .no_op;
5897 } else if (res.val.isZero(p.comp) and to.isPtr()) {
5898 cast_kind = .null_to_pointer;
5899 } else if (to.isScalar()) cast: {
5900 const old_float = res.ty.isFloat();
5901 const new_float = to.isFloat();
5902
5903 if (new_float and res.ty.isPtr()) {
5904 try p.errStr(.invalid_cast_to_float, l_paren, try p.typeStr(to));
5905 return error.ParsingFailed;
5906 } else if (old_float and to.isPtr()) {
5907 try p.errStr(.invalid_cast_to_pointer, l_paren, try p.typeStr(res.ty));
5908 return error.ParsingFailed;
5909 }
5910 const old_real = res.ty.isReal();
5911 const new_real = to.isReal();
5912
5913 if (to.eql(res.ty, p.comp, false)) {
5914 cast_kind = .no_op;
5915 } else if (to.is(.bool)) {
5916 if (res.ty.isPtr()) {
5917 cast_kind = .pointer_to_bool;
5918 } else if (res.ty.isInt()) {
5919 if (!old_real) {
5920 res.ty = res.ty.makeReal();
5921 try res.implicitCast(p, .complex_int_to_real);
5922 }
5923 cast_kind = .int_to_bool;
5924 } else if (old_float) {
5925 if (!old_real) {
5926 res.ty = res.ty.makeReal();
5927 try res.implicitCast(p, .complex_float_to_real);
5928 }
5929 cast_kind = .float_to_bool;
5930 }
5931 } else if (to.isInt()) {
5932 if (res.ty.is(.bool)) {
5933 if (!new_real) {
5934 res.ty = to.makeReal();
5935 try res.implicitCast(p, .bool_to_int);
5936 cast_kind = .real_to_complex_int;
5937 } else {
5938 cast_kind = .bool_to_int;
5939 }
5940 } else if (res.ty.isInt()) {
5941 if (old_real and new_real) {
5942 cast_kind = .int_cast;
5943 } else if (old_real) {
5944 res.ty = to.makeReal();
5945 try res.implicitCast(p, .int_cast);
5946 cast_kind = .real_to_complex_int;
5947 } else if (new_real) {
5948 res.ty = res.ty.makeReal();
5949 try res.implicitCast(p, .complex_int_to_real);
5950 cast_kind = .int_cast;
5951 } else {
5952 cast_kind = .complex_int_cast;
5953 }
5954 } else if (res.ty.isPtr()) {
5955 if (!new_real) {
5956 res.ty = to.makeReal();
5957 try res.implicitCast(p, .pointer_to_int);
5958 cast_kind = .real_to_complex_int;
5959 } else {
5960 cast_kind = .pointer_to_int;
5961 }
5962 } else if (old_real and new_real) {
5963 cast_kind = .float_to_int;
5964 } else if (old_real) {
5965 res.ty = to.makeReal();
5966 try res.implicitCast(p, .float_to_int);
5967 cast_kind = .real_to_complex_int;
5968 } else if (new_real) {
5969 res.ty = res.ty.makeReal();
5970 try res.implicitCast(p, .complex_float_to_real);
5971 cast_kind = .float_to_int;
5972 } else {
5973 cast_kind = .complex_float_to_complex_int;
5974 }
5975 } else if (to.isPtr()) {
5976 if (res.ty.isArray())
5977 cast_kind = .array_to_pointer
5978 else if (res.ty.isPtr())
5979 cast_kind = .bitcast
5980 else if (res.ty.isFunc())
5981 cast_kind = .function_to_pointer
5982 else if (res.ty.is(.bool))
5983 cast_kind = .bool_to_pointer
5984 else if (res.ty.isInt()) {
5985 if (!old_real) {
5986 res.ty = res.ty.makeReal();
5987 try res.implicitCast(p, .complex_int_to_real);
5988 }
5989 cast_kind = .int_to_pointer;
5990 } else {
5991 try p.errStr(.cond_expr_type, operand_tok, try p.typeStr(res.ty));
5992 return error.ParsingFailed;
5993 }
5994 } else if (new_float) {
5995 if (res.ty.is(.bool)) {
5996 if (!new_real) {
5997 res.ty = to.makeReal();
5998 try res.implicitCast(p, .bool_to_float);
5999 cast_kind = .real_to_complex_float;
6000 } else {
6001 cast_kind = .bool_to_float;
6002 }
6003 } else if (res.ty.isInt()) {
6004 if (old_real and new_real) {
6005 cast_kind = .int_to_float;
6006 } else if (old_real) {
6007 res.ty = to.makeReal();
6008 try res.implicitCast(p, .int_to_float);
6009 cast_kind = .real_to_complex_float;
6010 } else if (new_real) {
6011 res.ty = res.ty.makeReal();
6012 try res.implicitCast(p, .complex_int_to_real);
6013 cast_kind = .int_to_float;
6014 } else {
6015 cast_kind = .complex_int_to_complex_float;
6016 }
6017 } else if (old_real and new_real) {
6018 cast_kind = .float_cast;
6019 } else if (old_real) {
6020 res.ty = to.makeReal();
6021 try res.implicitCast(p, .float_cast);
6022 cast_kind = .real_to_complex_float;
6023 } else if (new_real) {
6024 res.ty = res.ty.makeReal();
6025 try res.implicitCast(p, .complex_float_to_real);
6026 cast_kind = .float_cast;
6027 } else {
6028 cast_kind = .complex_float_cast;
6029 }
6030 }
6031 if (res.val.opt_ref == .none) break :cast;
6032
6033 const old_int = res.ty.isInt() or res.ty.isPtr();
6034 const new_int = to.isInt() or to.isPtr();
6035 if (to.is(.bool)) {
6036 res.val.boolCast(p.comp);
6037 } else if (old_float and new_int) {
6038 if (to.hasIncompleteSize()) {
6039 try p.errStr(.cast_to_incomplete_type, l_paren, try p.typeStr(to));
6040 return error.ParsingFailed;
6041 }
6042 // Explicit cast, no conversion warning
6043 _ = try res.val.floatToInt(to, p.comp);
6044 } else if (new_float and old_int) {
6045 try res.val.intToFloat(to, p.comp);
6046 } else if (new_float and old_float) {
6047 try res.val.floatCast(to, p.comp);
6048 } else if (old_int and new_int) {
6049 if (to.hasIncompleteSize()) {
6050 try p.errStr(.cast_to_incomplete_type, l_paren, try p.typeStr(to));
6051 return error.ParsingFailed;
6052 }
6053 _ = try res.val.intCast(to, p.comp);
6054 }
6055 } else if (to.get(.@"union")) |union_ty| {
6056 if (union_ty.data.record.hasFieldOfType(res.ty, p.comp)) {
6057 cast_kind = .union_cast;
6058 try p.errTok(.gnu_union_cast, l_paren);
6059 } else {
6060 if (union_ty.data.record.isIncomplete()) {
6061 try p.errStr(.cast_to_incomplete_type, l_paren, try p.typeStr(to));
6062 } else {
6063 try p.errStr(.invalid_union_cast, l_paren, try p.typeStr(res.ty));
6064 }
6065 return error.ParsingFailed;
6066 }
6067 } else {
6068 if (to.is(.auto_type)) {
6069 try p.errTok(.invalid_cast_to_auto_type, l_paren);
6070 } else {
6071 try p.errStr(.invalid_cast_type, l_paren, try p.typeStr(to));
6072 }
6073 return error.ParsingFailed;
6074 }
6075 if (to.anyQual()) try p.errStr(.qual_cast, l_paren, try p.typeStr(to));
6076 if (to.isInt() and res.ty.isPtr() and to.sizeCompare(res.ty, p.comp) == .lt) {
6077 try p.errStr(.cast_to_smaller_int, l_paren, try p.typePairStrExtra(to, " from ", res.ty));
6078 }
6079 res.ty = to;
6080 res.ty.qual = .{};
6081 res.node = try p.addNode(.{
6082 .tag = .explicit_cast,
6083 .ty = res.ty,
6084 .data = .{ .cast = .{ .operand = res.node, .kind = cast_kind } },
6085 .loc = @enumFromInt(l_paren),
6086 });
6087 }
6088
6089 fn intFitsInType(res: Result, p: *Parser, ty: Type) !bool {
6090 const max_int = try Value.maxInt(ty, p.comp);
6091 const min_int = try Value.minInt(ty, p.comp);
6092 return res.val.compare(.lte, max_int, p.comp) and
6093 (res.ty.isUnsignedInt(p.comp) or res.val.compare(.gte, min_int, p.comp));
6094 }
6095
6096 const CoerceContext = union(enum) {
6097 assign,
6098 init,
6099 ret,
6100 arg: TokenIndex,
6101 test_coerce,
6102
6103 fn note(c: CoerceContext, p: *Parser) !void {
6104 switch (c) {
6105 .arg => |tok| try p.errTok(.parameter_here, tok),
6106 .test_coerce => unreachable,
6107 else => {},
6108 }
6109 }
6110
6111 fn typePairStr(c: CoerceContext, p: *Parser, dest_ty: Type, src_ty: Type) ![]const u8 {
6112 switch (c) {
6113 .assign, .init => return p.typePairStrExtra(dest_ty, " from incompatible type ", src_ty),
6114 .ret => return p.typePairStrExtra(src_ty, " from a function with incompatible result type ", dest_ty),
6115 .arg => return p.typePairStrExtra(src_ty, " to parameter of incompatible type ", dest_ty),
6116 .test_coerce => unreachable,
6117 }
6118 }
6119 };
6120
6121 /// Perform assignment-like coercion to `dest_ty`.
6122 fn coerce(res: *Result, p: *Parser, dest_ty: Type, tok: TokenIndex, c: CoerceContext) Error!void {
6123 if (res.ty.specifier == .invalid or dest_ty.specifier == .invalid) {
6124 res.ty = Type.invalid;
6125 return;
6126 }
6127 return res.coerceExtra(p, dest_ty, tok, c) catch |er| switch (er) {
6128 error.CoercionFailed => unreachable,
6129 else => |e| return e,
6130 };
6131 }
6132
6133 fn coerceExtra(
6134 res: *Result,
6135 p: *Parser,
6136 dest_ty: Type,
6137 tok: TokenIndex,
6138 c: CoerceContext,
6139 ) (Error || error{CoercionFailed})!void {
6140 // Subject of the coercion does not need to be qualified.
6141 var unqual_ty = dest_ty.canonicalize(.standard);
6142 unqual_ty.qual = .{};
6143 if (unqual_ty.is(.nullptr_t)) {
6144 if (res.ty.is(.nullptr_t)) return;
6145 } else if (unqual_ty.is(.bool)) {
6146 if (res.ty.isScalar() and !res.ty.is(.nullptr_t)) {
6147 // this is ridiculous but it's what clang does
6148 try res.boolCast(p, unqual_ty, tok);
6149 return;
6150 }
6151 } else if (unqual_ty.isInt()) {
6152 if (res.ty.isInt() or res.ty.isFloat()) {
6153 try res.intCast(p, unqual_ty, tok);
6154 return;
6155 } else if (res.ty.isPtr()) {
6156 if (c == .test_coerce) return error.CoercionFailed;
6157 try p.errStr(.implicit_ptr_to_int, tok, try p.typePairStrExtra(res.ty, " to ", dest_ty));
6158 try c.note(p);
6159 try res.intCast(p, unqual_ty, tok);
6160 return;
6161 }
6162 } else if (unqual_ty.isFloat()) {
6163 if (res.ty.isInt() or res.ty.isFloat()) {
6164 try res.floatCast(p, unqual_ty);
6165 return;
6166 }
6167 } else if (unqual_ty.isPtr()) {
6168 if (res.ty.is(.nullptr_t) or res.val.isZero(p.comp)) {
6169 try res.nullCast(p, dest_ty);
6170 return;
6171 } else if (res.ty.isInt() and res.ty.isReal()) {
6172 if (c == .test_coerce) return error.CoercionFailed;
6173 try p.errStr(.implicit_int_to_ptr, tok, try p.typePairStrExtra(res.ty, " to ", dest_ty));
6174 try c.note(p);
6175 try res.ptrCast(p, unqual_ty);
6176 return;
6177 } else if (res.ty.isVoidStar() or unqual_ty.eql(res.ty, p.comp, true)) {
6178 return; // ok
6179 } else if (unqual_ty.isVoidStar() and res.ty.isPtr() or (res.ty.isInt() and res.ty.isReal())) {
6180 return; // ok
6181 } else if (unqual_ty.eql(res.ty, p.comp, false)) {
6182 if (!unqual_ty.elemType().qual.hasQuals(res.ty.elemType().qual)) {
6183 try p.errStr(switch (c) {
6184 .assign => .ptr_assign_discards_quals,
6185 .init => .ptr_init_discards_quals,
6186 .ret => .ptr_ret_discards_quals,
6187 .arg => .ptr_arg_discards_quals,
6188 .test_coerce => return error.CoercionFailed,
6189 }, tok, try c.typePairStr(p, dest_ty, res.ty));
6190 }
6191 try res.ptrCast(p, unqual_ty);
6192 return;
6193 } else if (res.ty.isPtr()) {
6194 const different_sign_only = unqual_ty.elemType().sameRankDifferentSign(res.ty.elemType(), p.comp);
6195 try p.errStr(switch (c) {
6196 .assign => ([2]Diagnostics.Tag{ .incompatible_ptr_assign, .incompatible_ptr_assign_sign })[@intFromBool(different_sign_only)],
6197 .init => ([2]Diagnostics.Tag{ .incompatible_ptr_init, .incompatible_ptr_init_sign })[@intFromBool(different_sign_only)],
6198 .ret => ([2]Diagnostics.Tag{ .incompatible_return, .incompatible_return_sign })[@intFromBool(different_sign_only)],
6199 .arg => ([2]Diagnostics.Tag{ .incompatible_ptr_arg, .incompatible_ptr_arg_sign })[@intFromBool(different_sign_only)],
6200 .test_coerce => return error.CoercionFailed,
6201 }, tok, try c.typePairStr(p, dest_ty, res.ty));
6202 try c.note(p);
6203 try res.ptrChildTypeCast(p, unqual_ty);
6204 return;
6205 }
6206 } else if (unqual_ty.isRecord()) {
6207 if (unqual_ty.eql(res.ty, p.comp, false)) {
6208 return; // ok
6209 }
6210
6211 if (c == .arg) if (unqual_ty.get(.@"union")) |union_ty| {
6212 if (dest_ty.hasAttribute(.transparent_union)) transparent_union: {
6213 res.coerceExtra(p, union_ty.data.record.fields[0].ty, tok, .test_coerce) catch |er| switch (er) {
6214 error.CoercionFailed => break :transparent_union,
6215 else => |e| return e,
6216 };
6217 res.node = try p.addNode(.{
6218 .tag = .union_init_expr,
6219 .ty = dest_ty,
6220 .data = .{ .union_init = .{ .field_index = 0, .node = res.node } },
6221 });
6222 res.ty = dest_ty;
6223 return;
6224 }
6225 };
6226 } else if (unqual_ty.is(.vector)) {
6227 if (unqual_ty.eql(res.ty, p.comp, false)) {
6228 return; // ok
6229 }
6230 } else {
6231 if (c == .assign and (unqual_ty.isArray() or unqual_ty.isFunc())) {
6232 try p.errTok(.not_assignable, tok);
6233 return;
6234 } else if (c == .test_coerce) {
6235 return error.CoercionFailed;
6236 }
6237 // This case should not be possible and an error should have already been emitted but we
6238 // might still have attempted to parse further so return error.ParsingFailed here to stop.
6239 return error.ParsingFailed;
6240 }
6241
6242 try p.errStr(switch (c) {
6243 .assign => .incompatible_assign,
6244 .init => .incompatible_init,
6245 .ret => .incompatible_return,
6246 .arg => .incompatible_arg,
6247 .test_coerce => return error.CoercionFailed,
6248 }, tok, try c.typePairStr(p, dest_ty, res.ty));
6249 try c.note(p);
6250 }
6251};
6252
6253/// expr : assignExpr (',' assignExpr)*
6254fn expr(p: *Parser) Error!Result {
6255 var expr_start = p.tok_i;
6256 var err_start = p.comp.diagnostics.list.items.len;
6257 var lhs = try p.assignExpr();
6258 if (p.tok_ids[p.tok_i] == .comma) try lhs.expect(p);
6259 while (p.eatToken(.comma)) |comma| {
6260 try lhs.maybeWarnUnused(p, expr_start, err_start);
6261 expr_start = p.tok_i;
6262 err_start = p.comp.diagnostics.list.items.len;
6263
6264 var rhs = try p.assignExpr();
6265 try rhs.expect(p);
6266 try rhs.lvalConversion(p);
6267 lhs.val = rhs.val;
6268 lhs.ty = rhs.ty;
6269 try lhs.bin(p, .comma_expr, rhs, comma);
6270 }
6271 return lhs;
6272}
6273
6274fn tokToTag(p: *Parser, tok: TokenIndex) Tree.Tag {
6275 return switch (p.tok_ids[tok]) {
6276 .equal => .assign_expr,
6277 .asterisk_equal => .mul_assign_expr,
6278 .slash_equal => .div_assign_expr,
6279 .percent_equal => .mod_assign_expr,
6280 .plus_equal => .add_assign_expr,
6281 .minus_equal => .sub_assign_expr,
6282 .angle_bracket_angle_bracket_left_equal => .shl_assign_expr,
6283 .angle_bracket_angle_bracket_right_equal => .shr_assign_expr,
6284 .ampersand_equal => .bit_and_assign_expr,
6285 .caret_equal => .bit_xor_assign_expr,
6286 .pipe_equal => .bit_or_assign_expr,
6287 .equal_equal => .equal_expr,
6288 .bang_equal => .not_equal_expr,
6289 .angle_bracket_left => .less_than_expr,
6290 .angle_bracket_left_equal => .less_than_equal_expr,
6291 .angle_bracket_right => .greater_than_expr,
6292 .angle_bracket_right_equal => .greater_than_equal_expr,
6293 .angle_bracket_angle_bracket_left => .shl_expr,
6294 .angle_bracket_angle_bracket_right => .shr_expr,
6295 .plus => .add_expr,
6296 .minus => .sub_expr,
6297 .asterisk => .mul_expr,
6298 .slash => .div_expr,
6299 .percent => .mod_expr,
6300 else => unreachable,
6301 };
6302}
6303
6304/// assignExpr
6305/// : condExpr
6306/// | unExpr ('=' | '*=' | '/=' | '%=' | '+=' | '-=' | '<<=' | '>>=' | '&=' | '^=' | '|=') assignExpr
6307fn assignExpr(p: *Parser) Error!Result {
6308 var lhs = try p.condExpr();
6309 if (lhs.empty(p)) return lhs;
6310
6311 const tok = p.tok_i;
6312 const eq = p.eatToken(.equal);
6313 const mul = eq orelse p.eatToken(.asterisk_equal);
6314 const div = mul orelse p.eatToken(.slash_equal);
6315 const mod = div orelse p.eatToken(.percent_equal);
6316 const add = mod orelse p.eatToken(.plus_equal);
6317 const sub = add orelse p.eatToken(.minus_equal);
6318 const shl = sub orelse p.eatToken(.angle_bracket_angle_bracket_left_equal);
6319 const shr = shl orelse p.eatToken(.angle_bracket_angle_bracket_right_equal);
6320 const bit_and = shr orelse p.eatToken(.ampersand_equal);
6321 const bit_xor = bit_and orelse p.eatToken(.caret_equal);
6322 const bit_or = bit_xor orelse p.eatToken(.pipe_equal);
6323
6324 const tag = p.tokToTag(bit_or orelse return lhs);
6325 var rhs = try p.assignExpr();
6326 try rhs.expect(p);
6327 try rhs.lvalConversion(p);
6328
6329 var is_const: bool = undefined;
6330 if (!p.tmpTree().isLvalExtra(lhs.node, &is_const) or is_const) {
6331 try p.errTok(.not_assignable, tok);
6332 return error.ParsingFailed;
6333 }
6334
6335 // adjustTypes will do do lvalue conversion but we do not want that
6336 var lhs_copy = lhs;
6337 switch (tag) {
6338 .assign_expr => {}, // handle plain assignment separately
6339 .mul_assign_expr,
6340 .div_assign_expr,
6341 .mod_assign_expr,
6342 => {
6343 if (rhs.val.isZero(p.comp) and lhs.ty.isInt() and rhs.ty.isInt()) {
6344 switch (tag) {
6345 .div_assign_expr => try p.errStr(.division_by_zero, div.?, "division"),
6346 .mod_assign_expr => try p.errStr(.division_by_zero, mod.?, "remainder"),
6347 else => {},
6348 }
6349 }
6350 _ = try lhs_copy.adjustTypes(tok, &rhs, p, if (tag == .mod_assign_expr) .integer else .arithmetic);
6351 try lhs.bin(p, tag, rhs, bit_or.?);
6352 return lhs;
6353 },
6354 .sub_assign_expr,
6355 .add_assign_expr,
6356 => {
6357 if (lhs.ty.isPtr() and rhs.ty.isInt()) {
6358 try rhs.ptrCast(p, lhs.ty);
6359 } else {
6360 _ = try lhs_copy.adjustTypes(tok, &rhs, p, .arithmetic);
6361 }
6362 try lhs.bin(p, tag, rhs, bit_or.?);
6363 return lhs;
6364 },
6365 .shl_assign_expr,
6366 .shr_assign_expr,
6367 .bit_and_assign_expr,
6368 .bit_xor_assign_expr,
6369 .bit_or_assign_expr,
6370 => {
6371 _ = try lhs_copy.adjustTypes(tok, &rhs, p, .integer);
6372 try lhs.bin(p, tag, rhs, bit_or.?);
6373 return lhs;
6374 },
6375 else => unreachable,
6376 }
6377
6378 try rhs.coerce(p, lhs.ty, tok, .assign);
6379
6380 try lhs.bin(p, tag, rhs, bit_or.?);
6381 return lhs;
6382}
6383
6384/// Returns a parse error if the expression is not an integer constant
6385/// integerConstExpr : constExpr
6386fn integerConstExpr(p: *Parser, decl_folding: ConstDeclFoldingMode) Error!Result {
6387 const start = p.tok_i;
6388 const res = try p.constExpr(decl_folding);
6389 if (!res.ty.isInt() and res.ty.specifier != .invalid) {
6390 try p.errTok(.expected_integer_constant_expr, start);
6391 return error.ParsingFailed;
6392 }
6393 return res;
6394}
6395
6396/// Caller is responsible for issuing a diagnostic if result is invalid/unavailable
6397/// constExpr : condExpr
6398fn constExpr(p: *Parser, decl_folding: ConstDeclFoldingMode) Error!Result {
6399 const const_decl_folding = p.const_decl_folding;
6400 defer p.const_decl_folding = const_decl_folding;
6401 p.const_decl_folding = decl_folding;
6402
6403 const res = try p.condExpr();
6404 try res.expect(p);
6405
6406 if (res.ty.specifier == .invalid or res.val.opt_ref == .none) return res;
6407
6408 // saveValue sets val to unavailable
6409 var copy = res;
6410 try copy.saveValue(p);
6411 return res;
6412}
6413
6414/// condExpr : lorExpr ('?' expression? ':' condExpr)?
6415fn condExpr(p: *Parser) Error!Result {
6416 const cond_tok = p.tok_i;
6417 var cond = try p.lorExpr();
6418 if (cond.empty(p) or p.eatToken(.question_mark) == null) return cond;
6419 try cond.lvalConversion(p);
6420 const saved_eval = p.no_eval;
6421
6422 if (!cond.ty.isScalar()) {
6423 try p.errStr(.cond_expr_type, cond_tok, try p.typeStr(cond.ty));
6424 return error.ParsingFailed;
6425 }
6426
6427 // Prepare for possible binary conditional expression.
6428 const maybe_colon = p.eatToken(.colon);
6429
6430 // Depending on the value of the condition, avoid evaluating unreachable branches.
6431 var then_expr = blk: {
6432 defer p.no_eval = saved_eval;
6433 if (cond.val.opt_ref != .none and !cond.val.toBool(p.comp)) p.no_eval = true;
6434 break :blk try p.expr();
6435 };
6436 try then_expr.expect(p);
6437
6438 // If we saw a colon then this is a binary conditional expression.
6439 if (maybe_colon) |colon| {
6440 var cond_then = cond;
6441 cond_then.node = try p.addNode(.{ .tag = .cond_dummy_expr, .ty = cond.ty, .data = .{ .un = cond.node } });
6442 _ = try cond_then.adjustTypes(colon, &then_expr, p, .conditional);
6443 cond.ty = then_expr.ty;
6444 cond.node = try p.addNode(.{
6445 .tag = .binary_cond_expr,
6446 .ty = cond.ty,
6447 .data = .{ .if3 = .{ .cond = cond.node, .body = (try p.addList(&.{ cond_then.node, then_expr.node })).start } },
6448 .loc = @enumFromInt(cond_tok),
6449 });
6450 return cond;
6451 }
6452
6453 const colon = try p.expectToken(.colon);
6454 var else_expr = blk: {
6455 defer p.no_eval = saved_eval;
6456 if (cond.val.opt_ref != .none and cond.val.toBool(p.comp)) p.no_eval = true;
6457 break :blk try p.condExpr();
6458 };
6459 try else_expr.expect(p);
6460
6461 _ = try then_expr.adjustTypes(colon, &else_expr, p, .conditional);
6462
6463 if (cond.val.opt_ref != .none) {
6464 cond.val = if (cond.val.toBool(p.comp)) then_expr.val else else_expr.val;
6465 } else {
6466 try then_expr.saveValue(p);
6467 try else_expr.saveValue(p);
6468 }
6469 cond.ty = then_expr.ty;
6470 cond.node = try p.addNode(.{
6471 .tag = .cond_expr,
6472 .ty = cond.ty,
6473 .data = .{ .if3 = .{ .cond = cond.node, .body = (try p.addList(&.{ then_expr.node, else_expr.node })).start } },
6474 .loc = @enumFromInt(cond_tok),
6475 });
6476 return cond;
6477}
6478
6479/// lorExpr : landExpr ('||' landExpr)*
6480fn lorExpr(p: *Parser) Error!Result {
6481 var lhs = try p.landExpr();
6482 if (lhs.empty(p)) return lhs;
6483 const saved_eval = p.no_eval;
6484 defer p.no_eval = saved_eval;
6485
6486 while (p.eatToken(.pipe_pipe)) |tok| {
6487 if (lhs.val.opt_ref != .none and lhs.val.toBool(p.comp)) p.no_eval = true;
6488 var rhs = try p.landExpr();
6489 try rhs.expect(p);
6490
6491 if (try lhs.adjustTypes(tok, &rhs, p, .boolean_logic)) {
6492 const res = lhs.val.toBool(p.comp) or rhs.val.toBool(p.comp);
6493 lhs.val = Value.fromBool(res);
6494 } else {
6495 lhs.val.boolCast(p.comp);
6496 }
6497 try lhs.boolRes(p, .bool_or_expr, rhs, tok);
6498 }
6499 return lhs;
6500}
6501
6502/// landExpr : orExpr ('&&' orExpr)*
6503fn landExpr(p: *Parser) Error!Result {
6504 var lhs = try p.orExpr();
6505 if (lhs.empty(p)) return lhs;
6506 const saved_eval = p.no_eval;
6507 defer p.no_eval = saved_eval;
6508
6509 while (p.eatToken(.ampersand_ampersand)) |tok| {
6510 if (lhs.val.opt_ref != .none and !lhs.val.toBool(p.comp)) p.no_eval = true;
6511 var rhs = try p.orExpr();
6512 try rhs.expect(p);
6513
6514 if (try lhs.adjustTypes(tok, &rhs, p, .boolean_logic)) {
6515 const res = lhs.val.toBool(p.comp) and rhs.val.toBool(p.comp);
6516 lhs.val = Value.fromBool(res);
6517 } else {
6518 lhs.val.boolCast(p.comp);
6519 }
6520 try lhs.boolRes(p, .bool_and_expr, rhs, tok);
6521 }
6522 return lhs;
6523}
6524
6525/// orExpr : xorExpr ('|' xorExpr)*
6526fn orExpr(p: *Parser) Error!Result {
6527 var lhs = try p.xorExpr();
6528 if (lhs.empty(p)) return lhs;
6529 while (p.eatToken(.pipe)) |tok| {
6530 var rhs = try p.xorExpr();
6531 try rhs.expect(p);
6532
6533 if (try lhs.adjustTypes(tok, &rhs, p, .integer)) {
6534 lhs.val = try lhs.val.bitOr(rhs.val, p.comp);
6535 }
6536 try lhs.bin(p, .bit_or_expr, rhs, tok);
6537 }
6538 return lhs;
6539}
6540
6541/// xorExpr : andExpr ('^' andExpr)*
6542fn xorExpr(p: *Parser) Error!Result {
6543 var lhs = try p.andExpr();
6544 if (lhs.empty(p)) return lhs;
6545 while (p.eatToken(.caret)) |tok| {
6546 var rhs = try p.andExpr();
6547 try rhs.expect(p);
6548
6549 if (try lhs.adjustTypes(tok, &rhs, p, .integer)) {
6550 lhs.val = try lhs.val.bitXor(rhs.val, p.comp);
6551 }
6552 try lhs.bin(p, .bit_xor_expr, rhs, tok);
6553 }
6554 return lhs;
6555}
6556
6557/// andExpr : eqExpr ('&' eqExpr)*
6558fn andExpr(p: *Parser) Error!Result {
6559 var lhs = try p.eqExpr();
6560 if (lhs.empty(p)) return lhs;
6561 while (p.eatToken(.ampersand)) |tok| {
6562 var rhs = try p.eqExpr();
6563 try rhs.expect(p);
6564
6565 if (try lhs.adjustTypes(tok, &rhs, p, .integer)) {
6566 lhs.val = try lhs.val.bitAnd(rhs.val, p.comp);
6567 }
6568 try lhs.bin(p, .bit_and_expr, rhs, tok);
6569 }
6570 return lhs;
6571}
6572
6573/// eqExpr : compExpr (('==' | '!=') compExpr)*
6574fn eqExpr(p: *Parser) Error!Result {
6575 var lhs = try p.compExpr();
6576 if (lhs.empty(p)) return lhs;
6577 while (true) {
6578 const eq = p.eatToken(.equal_equal);
6579 const ne = eq orelse p.eatToken(.bang_equal);
6580 const tag = p.tokToTag(ne orelse break);
6581 var rhs = try p.compExpr();
6582 try rhs.expect(p);
6583
6584 if (try lhs.adjustTypes(ne.?, &rhs, p, .equality)) {
6585 const op: std.math.CompareOperator = if (tag == .equal_expr) .eq else .neq;
6586 const res = lhs.val.compare(op, rhs.val, p.comp);
6587 lhs.val = Value.fromBool(res);
6588 } else {
6589 lhs.val.boolCast(p.comp);
6590 }
6591 try lhs.boolRes(p, tag, rhs, ne.?);
6592 }
6593 return lhs;
6594}
6595
6596/// compExpr : shiftExpr (('<' | '<=' | '>' | '>=') shiftExpr)*
6597fn compExpr(p: *Parser) Error!Result {
6598 var lhs = try p.shiftExpr();
6599 if (lhs.empty(p)) return lhs;
6600 while (true) {
6601 const lt = p.eatToken(.angle_bracket_left);
6602 const le = lt orelse p.eatToken(.angle_bracket_left_equal);
6603 const gt = le orelse p.eatToken(.angle_bracket_right);
6604 const ge = gt orelse p.eatToken(.angle_bracket_right_equal);
6605 const tag = p.tokToTag(ge orelse break);
6606 var rhs = try p.shiftExpr();
6607 try rhs.expect(p);
6608
6609 if (try lhs.adjustTypes(ge.?, &rhs, p, .relational)) {
6610 const op: std.math.CompareOperator = switch (tag) {
6611 .less_than_expr => .lt,
6612 .less_than_equal_expr => .lte,
6613 .greater_than_expr => .gt,
6614 .greater_than_equal_expr => .gte,
6615 else => unreachable,
6616 };
6617 const res = lhs.val.compare(op, rhs.val, p.comp);
6618 lhs.val = Value.fromBool(res);
6619 } else {
6620 lhs.val.boolCast(p.comp);
6621 }
6622 try lhs.boolRes(p, tag, rhs, ge.?);
6623 }
6624 return lhs;
6625}
6626
6627/// shiftExpr : addExpr (('<<' | '>>') addExpr)*
6628fn shiftExpr(p: *Parser) Error!Result {
6629 var lhs = try p.addExpr();
6630 if (lhs.empty(p)) return lhs;
6631 while (true) {
6632 const shl = p.eatToken(.angle_bracket_angle_bracket_left);
6633 const shr = shl orelse p.eatToken(.angle_bracket_angle_bracket_right);
6634 const tag = p.tokToTag(shr orelse break);
6635 var rhs = try p.addExpr();
6636 try rhs.expect(p);
6637
6638 if (try lhs.adjustTypes(shr.?, &rhs, p, .integer)) {
6639 if (rhs.val.compare(.lt, Value.zero, p.comp)) {
6640 try p.errStr(.negative_shift_count, shl orelse shr.?, try rhs.str(p));
6641 }
6642 if (rhs.val.compare(.gte, try Value.int(lhs.ty.bitSizeof(p.comp).?, p.comp), p.comp)) {
6643 try p.errStr(.too_big_shift_count, shl orelse shr.?, try rhs.str(p));
6644 }
6645 if (shl != null) {
6646 if (try lhs.val.shl(lhs.val, rhs.val, lhs.ty, p.comp) and
6647 lhs.ty.signedness(p.comp) != .unsigned) try p.errOverflow(shl.?, lhs);
6648 } else {
6649 lhs.val = try lhs.val.shr(rhs.val, lhs.ty, p.comp);
6650 }
6651 }
6652 try lhs.bin(p, tag, rhs, shr.?);
6653 }
6654 return lhs;
6655}
6656
6657/// addExpr : mulExpr (('+' | '-') mulExpr)*
6658fn addExpr(p: *Parser) Error!Result {
6659 var lhs = try p.mulExpr();
6660 if (lhs.empty(p)) return lhs;
6661 while (true) {
6662 const plus = p.eatToken(.plus);
6663 const minus = plus orelse p.eatToken(.minus);
6664 const tag = p.tokToTag(minus orelse break);
6665 var rhs = try p.mulExpr();
6666 try rhs.expect(p);
6667
6668 const lhs_ty = lhs.ty;
6669 if (try lhs.adjustTypes(minus.?, &rhs, p, if (plus != null) .add else .sub)) {
6670 if (plus != null) {
6671 if (try lhs.val.add(lhs.val, rhs.val, lhs.ty, p.comp) and
6672 lhs.ty.signedness(p.comp) != .unsigned) try p.errOverflow(plus.?, lhs);
6673 } else {
6674 if (try lhs.val.sub(lhs.val, rhs.val, lhs.ty, p.comp) and
6675 lhs.ty.signedness(p.comp) != .unsigned) try p.errOverflow(minus.?, lhs);
6676 }
6677 }
6678 if (lhs.ty.specifier != .invalid and lhs_ty.isPtr() and !lhs_ty.isVoidStar() and lhs_ty.elemType().hasIncompleteSize()) {
6679 try p.errStr(.ptr_arithmetic_incomplete, minus.?, try p.typeStr(lhs_ty.elemType()));
6680 lhs.ty = Type.invalid;
6681 }
6682 try lhs.bin(p, tag, rhs, minus.?);
6683 }
6684 return lhs;
6685}
6686
6687/// mulExpr : castExpr (('*' | '/' | '%') castExpr)*´
6688fn mulExpr(p: *Parser) Error!Result {
6689 var lhs = try p.castExpr();
6690 if (lhs.empty(p)) return lhs;
6691 while (true) {
6692 const mul = p.eatToken(.asterisk);
6693 const div = mul orelse p.eatToken(.slash);
6694 const percent = div orelse p.eatToken(.percent);
6695 const tag = p.tokToTag(percent orelse break);
6696 var rhs = try p.castExpr();
6697 try rhs.expect(p);
6698
6699 if (rhs.val.isZero(p.comp) and mul == null and !p.no_eval and lhs.ty.isInt() and rhs.ty.isInt()) {
6700 const err_tag: Diagnostics.Tag = if (p.in_macro) .division_by_zero_macro else .division_by_zero;
6701 lhs.val = .{};
6702 if (div != null) {
6703 try p.errStr(err_tag, div.?, "division");
6704 } else {
6705 try p.errStr(err_tag, percent.?, "remainder");
6706 }
6707 if (p.in_macro) return error.ParsingFailed;
6708 }
6709
6710 if (try lhs.adjustTypes(percent.?, &rhs, p, if (tag == .mod_expr) .integer else .arithmetic)) {
6711 if (mul != null) {
6712 if (try lhs.val.mul(lhs.val, rhs.val, lhs.ty, p.comp) and
6713 lhs.ty.signedness(p.comp) != .unsigned) try p.errOverflow(mul.?, lhs);
6714 } else if (div != null) {
6715 if (try lhs.val.div(lhs.val, rhs.val, lhs.ty, p.comp) and
6716 lhs.ty.signedness(p.comp) != .unsigned) try p.errOverflow(div.?, lhs);
6717 } else {
6718 var res = try Value.rem(lhs.val, rhs.val, lhs.ty, p.comp);
6719 if (res.opt_ref == .none) {
6720 if (p.in_macro) {
6721 // match clang behavior by defining invalid remainder to be zero in macros
6722 res = Value.zero;
6723 } else {
6724 try lhs.saveValue(p);
6725 try rhs.saveValue(p);
6726 }
6727 }
6728 lhs.val = res;
6729 }
6730 }
6731
6732 try lhs.bin(p, tag, rhs, percent.?);
6733 }
6734 return lhs;
6735}
6736
6737/// This will always be the last message, if present
6738fn removeUnusedWarningForTok(p: *Parser, last_expr_tok: TokenIndex) void {
6739 if (last_expr_tok == 0) return;
6740 if (p.comp.diagnostics.list.items.len == 0) return;
6741
6742 const last_expr_loc = p.pp.tokens.items(.loc)[last_expr_tok];
6743 const last_msg = p.comp.diagnostics.list.items[p.comp.diagnostics.list.items.len - 1];
6744
6745 if (last_msg.tag == .unused_value and last_msg.loc.eql(last_expr_loc)) {
6746 p.comp.diagnostics.list.items.len = p.comp.diagnostics.list.items.len - 1;
6747 }
6748}
6749
6750/// castExpr
6751/// : '(' compoundStmt ')' suffixExpr*
6752/// | '(' typeName ')' castExpr
6753/// | '(' typeName ')' '{' initializerItems '}'
6754/// | __builtin_choose_expr '(' integerConstExpr ',' assignExpr ',' assignExpr ')'
6755/// | __builtin_va_arg '(' assignExpr ',' typeName ')'
6756/// | __builtin_offsetof '(' typeName ',' offsetofMemberDesignator ')'
6757/// | __builtin_bitoffsetof '(' typeName ',' offsetofMemberDesignator ')'
6758/// | unExpr
6759fn castExpr(p: *Parser) Error!Result {
6760 if (p.eatToken(.l_paren)) |l_paren| cast_expr: {
6761 if (p.tok_ids[p.tok_i] == .l_brace) {
6762 const tok = p.tok_i;
6763 try p.err(.gnu_statement_expression);
6764 if (p.func.ty == null) {
6765 try p.err(.stmt_expr_not_allowed_file_scope);
6766 return error.ParsingFailed;
6767 }
6768 var stmt_expr_state: StmtExprState = .{};
6769 const body_node = (try p.compoundStmt(false, &stmt_expr_state)).?; // compoundStmt only returns null if .l_brace isn't the first token
6770 p.removeUnusedWarningForTok(stmt_expr_state.last_expr_tok);
6771
6772 var res = Result{
6773 .node = body_node,
6774 .ty = stmt_expr_state.last_expr_res.ty,
6775 .val = stmt_expr_state.last_expr_res.val,
6776 };
6777 try p.expectClosing(l_paren, .r_paren);
6778 try res.un(p, .stmt_expr, tok);
6779 while (true) {
6780 const suffix = try p.suffixExpr(res);
6781 if (suffix.empty(p)) break;
6782 res = suffix;
6783 }
6784 return res;
6785 }
6786 const ty = (try p.typeName()) orelse {
6787 p.tok_i -= 1;
6788 break :cast_expr;
6789 };
6790 try p.expectClosing(l_paren, .r_paren);
6791
6792 if (p.tok_ids[p.tok_i] == .l_brace) {
6793 // Compound literal; handled in unExpr
6794 p.tok_i = l_paren;
6795 break :cast_expr;
6796 }
6797
6798 const operand_tok = p.tok_i;
6799 var operand = try p.castExpr();
6800 try operand.expect(p);
6801 try operand.lvalConversion(p);
6802 try operand.castType(p, ty, operand_tok, l_paren);
6803 return operand;
6804 }
6805 switch (p.tok_ids[p.tok_i]) {
6806 .builtin_choose_expr => return p.builtinChooseExpr(),
6807 .builtin_va_arg => return p.builtinVaArg(),
6808 .builtin_offsetof => return p.builtinOffsetof(false),
6809 .builtin_bitoffsetof => return p.builtinOffsetof(true),
6810 .builtin_types_compatible_p => return p.typesCompatible(),
6811 // TODO: other special-cased builtins
6812 else => {},
6813 }
6814 return p.unExpr();
6815}
6816
6817fn typesCompatible(p: *Parser) Error!Result {
6818 const builtin_tok = p.tok_i;
6819 p.tok_i += 1;
6820 const l_paren = try p.expectToken(.l_paren);
6821
6822 const first_tok = p.tok_i;
6823 const first = (try p.typeName()) orelse {
6824 try p.err(.expected_type);
6825 p.skipTo(.r_paren);
6826 return error.ParsingFailed;
6827 };
6828 const lhs = try p.addNode(.{ .tag = .invalid, .ty = first, .data = undefined, .loc = @enumFromInt(first_tok) });
6829 _ = try p.expectToken(.comma);
6830
6831 const second_tok = p.tok_i;
6832 const second = (try p.typeName()) orelse {
6833 try p.err(.expected_type);
6834 p.skipTo(.r_paren);
6835 return error.ParsingFailed;
6836 };
6837 const rhs = try p.addNode(.{ .tag = .invalid, .ty = second, .data = undefined, .loc = @enumFromInt(second_tok) });
6838
6839 try p.expectClosing(l_paren, .r_paren);
6840
6841 var first_unqual = first.canonicalize(.standard);
6842 first_unqual.qual.@"const" = false;
6843 first_unqual.qual.@"volatile" = false;
6844 var second_unqual = second.canonicalize(.standard);
6845 second_unqual.qual.@"const" = false;
6846 second_unqual.qual.@"volatile" = false;
6847
6848 const compatible = first_unqual.eql(second_unqual, p.comp, true);
6849
6850 const res = Result{
6851 .val = Value.fromBool(compatible),
6852 .node = try p.addNode(.{
6853 .tag = .builtin_types_compatible_p,
6854 .ty = Type.int,
6855 .data = .{ .bin = .{
6856 .lhs = lhs,
6857 .rhs = rhs,
6858 } },
6859 .loc = @enumFromInt(builtin_tok),
6860 }),
6861 };
6862 try p.value_map.put(res.node, res.val);
6863 return res;
6864}
6865
6866fn builtinChooseExpr(p: *Parser) Error!Result {
6867 p.tok_i += 1;
6868 const l_paren = try p.expectToken(.l_paren);
6869 const cond_tok = p.tok_i;
6870 var cond = try p.integerConstExpr(.no_const_decl_folding);
6871 if (cond.val.opt_ref == .none) {
6872 try p.errTok(.builtin_choose_cond, cond_tok);
6873 return error.ParsingFailed;
6874 }
6875
6876 _ = try p.expectToken(.comma);
6877
6878 var then_expr = if (cond.val.toBool(p.comp)) try p.assignExpr() else try p.parseNoEval(assignExpr);
6879 try then_expr.expect(p);
6880
6881 _ = try p.expectToken(.comma);
6882
6883 var else_expr = if (!cond.val.toBool(p.comp)) try p.assignExpr() else try p.parseNoEval(assignExpr);
6884 try else_expr.expect(p);
6885
6886 try p.expectClosing(l_paren, .r_paren);
6887
6888 if (cond.val.toBool(p.comp)) {
6889 cond.val = then_expr.val;
6890 cond.ty = then_expr.ty;
6891 } else {
6892 cond.val = else_expr.val;
6893 cond.ty = else_expr.ty;
6894 }
6895 cond.node = try p.addNode(.{
6896 .tag = .builtin_choose_expr,
6897 .ty = cond.ty,
6898 .data = .{ .if3 = .{ .cond = cond.node, .body = (try p.addList(&.{ then_expr.node, else_expr.node })).start } },
6899 });
6900 return cond;
6901}
6902
6903fn builtinVaArg(p: *Parser) Error!Result {
6904 const builtin_tok = p.tok_i;
6905 p.tok_i += 1;
6906
6907 const l_paren = try p.expectToken(.l_paren);
6908 const va_list_tok = p.tok_i;
6909 var va_list = try p.assignExpr();
6910 try va_list.expect(p);
6911 try va_list.lvalConversion(p);
6912
6913 _ = try p.expectToken(.comma);
6914
6915 const ty = (try p.typeName()) orelse {
6916 try p.err(.expected_type);
6917 return error.ParsingFailed;
6918 };
6919 try p.expectClosing(l_paren, .r_paren);
6920
6921 if (!va_list.ty.eql(p.comp.types.va_list, p.comp, true)) {
6922 try p.errStr(.incompatible_va_arg, va_list_tok, try p.typeStr(va_list.ty));
6923 return error.ParsingFailed;
6924 }
6925
6926 return Result{ .ty = ty, .node = try p.addNode(.{
6927 .tag = .special_builtin_call_one,
6928 .ty = ty,
6929 .data = .{ .decl = .{ .name = builtin_tok, .node = va_list.node } },
6930 }) };
6931}
6932
6933fn builtinOffsetof(p: *Parser, want_bits: bool) Error!Result {
6934 const builtin_tok = p.tok_i;
6935 p.tok_i += 1;
6936
6937 const l_paren = try p.expectToken(.l_paren);
6938 const ty_tok = p.tok_i;
6939
6940 const ty = (try p.typeName()) orelse {
6941 try p.err(.expected_type);
6942 p.skipTo(.r_paren);
6943 return error.ParsingFailed;
6944 };
6945
6946 if (!ty.isRecord()) {
6947 try p.errStr(.offsetof_ty, ty_tok, try p.typeStr(ty));
6948 p.skipTo(.r_paren);
6949 return error.ParsingFailed;
6950 } else if (ty.hasIncompleteSize()) {
6951 try p.errStr(.offsetof_incomplete, ty_tok, try p.typeStr(ty));
6952 p.skipTo(.r_paren);
6953 return error.ParsingFailed;
6954 }
6955
6956 _ = try p.expectToken(.comma);
6957
6958 const offsetof_expr = try p.offsetofMemberDesignator(ty, want_bits);
6959
6960 try p.expectClosing(l_paren, .r_paren);
6961
6962 return Result{
6963 .ty = p.comp.types.size,
6964 .val = offsetof_expr.val,
6965 .node = try p.addNode(.{
6966 .tag = .special_builtin_call_one,
6967 .ty = p.comp.types.size,
6968 .data = .{ .decl = .{ .name = builtin_tok, .node = offsetof_expr.node } },
6969 }),
6970 };
6971}
6972
6973/// offsetofMemberDesignator: IDENTIFIER ('.' IDENTIFIER | '[' expr ']' )*
6974fn offsetofMemberDesignator(p: *Parser, base_ty: Type, want_bits: bool) Error!Result {
6975 errdefer p.skipTo(.r_paren);
6976 const base_field_name_tok = try p.expectIdentifier();
6977 const base_field_name = try StrInt.intern(p.comp, p.tokSlice(base_field_name_tok));
6978 const base_record_ty = base_ty.getRecord().?;
6979 try p.validateFieldAccess(base_record_ty, base_ty, base_field_name_tok, base_field_name);
6980 const base_node = try p.addNode(.{ .tag = .default_init_expr, .ty = base_ty, .data = undefined });
6981
6982 var cur_offset: u64 = 0;
6983 var lhs = try p.fieldAccessExtra(base_node, base_record_ty, base_field_name, false, &cur_offset);
6984
6985 var total_offset = cur_offset;
6986 while (true) switch (p.tok_ids[p.tok_i]) {
6987 .period => {
6988 p.tok_i += 1;
6989 const field_name_tok = try p.expectIdentifier();
6990 const field_name = try StrInt.intern(p.comp, p.tokSlice(field_name_tok));
6991
6992 const lhs_record_ty = lhs.ty.getRecord() orelse {
6993 try p.errStr(.offsetof_ty, field_name_tok, try p.typeStr(lhs.ty));
6994 return error.ParsingFailed;
6995 };
6996 try p.validateFieldAccess(lhs_record_ty, lhs.ty, field_name_tok, field_name);
6997 lhs = try p.fieldAccessExtra(lhs.node, lhs_record_ty, field_name, false, &cur_offset);
6998 total_offset += cur_offset;
6999 },
7000 .l_bracket => {
7001 const l_bracket_tok = p.tok_i;
7002 p.tok_i += 1;
7003 var index = try p.expr();
7004 try index.expect(p);
7005 _ = try p.expectClosing(l_bracket_tok, .r_bracket);
7006
7007 if (!lhs.ty.isArray()) {
7008 try p.errStr(.offsetof_array, l_bracket_tok, try p.typeStr(lhs.ty));
7009 return error.ParsingFailed;
7010 }
7011 var ptr = lhs;
7012 try ptr.lvalConversion(p);
7013 try index.lvalConversion(p);
7014
7015 if (index.ty.isInt()) {
7016 try p.checkArrayBounds(index, lhs, l_bracket_tok);
7017 } else {
7018 try p.errTok(.invalid_index, l_bracket_tok);
7019 }
7020
7021 try index.saveValue(p);
7022 try ptr.bin(p, .array_access_expr, index, l_bracket_tok);
7023 lhs = ptr;
7024 },
7025 else => break,
7026 };
7027 const val = try Value.int(if (want_bits) total_offset else total_offset / 8, p.comp);
7028 return Result{ .ty = base_ty, .val = val, .node = lhs.node };
7029}
7030
7031/// unExpr
7032/// : (compoundLiteral | primaryExpr) suffixExpr*
7033/// | '&&' IDENTIFIER
7034/// | ('&' | '*' | '+' | '-' | '~' | '!' | '++' | '--' | keyword_extension | keyword_imag | keyword_real) castExpr
7035/// | keyword_sizeof unExpr
7036/// | keyword_sizeof '(' typeName ')'
7037/// | keyword_alignof '(' typeName ')'
7038/// | keyword_c23_alignof '(' typeName ')'
7039fn unExpr(p: *Parser) Error!Result {
7040 const tok = p.tok_i;
7041 switch (p.tok_ids[tok]) {
7042 .ampersand_ampersand => {
7043 const address_tok = p.tok_i;
7044 p.tok_i += 1;
7045 const name_tok = try p.expectIdentifier();
7046 try p.errTok(.gnu_label_as_value, address_tok);
7047 p.contains_address_of_label = true;
7048
7049 const str = p.tokSlice(name_tok);
7050 if (p.findLabel(str) == null) {
7051 try p.labels.append(.{ .unresolved_goto = name_tok });
7052 }
7053 const elem_ty = try p.arena.create(Type);
7054 elem_ty.* = .{ .specifier = .void };
7055 const result_ty = Type{ .specifier = .pointer, .data = .{ .sub_type = elem_ty } };
7056 return Result{
7057 .node = try p.addNode(.{
7058 .tag = .addr_of_label,
7059 .data = .{ .decl_ref = name_tok },
7060 .ty = result_ty,
7061 .loc = @enumFromInt(address_tok),
7062 }),
7063 .ty = result_ty,
7064 };
7065 },
7066 .ampersand => {
7067 if (p.in_macro) {
7068 try p.err(.invalid_preproc_operator);
7069 return error.ParsingFailed;
7070 }
7071 p.tok_i += 1;
7072 var operand = try p.castExpr();
7073 try operand.expect(p);
7074
7075 const tree = p.tmpTree();
7076 if (p.getNode(operand.node, .member_access_expr) orelse
7077 p.getNode(operand.node, .member_access_ptr_expr)) |member_node|
7078 {
7079 if (tree.isBitfield(member_node)) try p.errTok(.addr_of_bitfield, tok);
7080 }
7081 if (!tree.isLval(operand.node) and !operand.ty.is(.invalid)) {
7082 try p.errTok(.addr_of_rvalue, tok);
7083 }
7084 if (operand.ty.qual.register) try p.errTok(.addr_of_register, tok);
7085
7086 if (!operand.ty.is(.invalid)) {
7087 const elem_ty = try p.arena.create(Type);
7088 elem_ty.* = operand.ty;
7089 operand.ty = Type{
7090 .specifier = .pointer,
7091 .data = .{ .sub_type = elem_ty },
7092 };
7093 }
7094 try operand.saveValue(p);
7095 try operand.un(p, .addr_of_expr, tok);
7096 return operand;
7097 },
7098 .asterisk => {
7099 const asterisk_loc = p.tok_i;
7100 p.tok_i += 1;
7101 var operand = try p.castExpr();
7102 try operand.expect(p);
7103
7104 if (operand.ty.isArray() or operand.ty.isPtr() or operand.ty.isFunc()) {
7105 try operand.lvalConversion(p);
7106 operand.ty = operand.ty.elemType();
7107 } else {
7108 try p.errTok(.indirection_ptr, tok);
7109 }
7110 if (operand.ty.hasIncompleteSize() and !operand.ty.is(.void)) {
7111 try p.errStr(.deref_incomplete_ty_ptr, asterisk_loc, try p.typeStr(operand.ty));
7112 }
7113 operand.ty.qual = .{};
7114 try operand.un(p, .deref_expr, tok);
7115 return operand;
7116 },
7117 .plus => {
7118 p.tok_i += 1;
7119
7120 var operand = try p.castExpr();
7121 try operand.expect(p);
7122 try operand.lvalConversion(p);
7123 if (!operand.ty.isInt() and !operand.ty.isFloat())
7124 try p.errStr(.invalid_argument_un, tok, try p.typeStr(operand.ty));
7125
7126 try operand.usualUnaryConversion(p, tok);
7127
7128 return operand;
7129 },
7130 .minus => {
7131 p.tok_i += 1;
7132
7133 var operand = try p.castExpr();
7134 try operand.expect(p);
7135 try operand.lvalConversion(p);
7136 if (!operand.ty.isInt() and !operand.ty.isFloat())
7137 try p.errStr(.invalid_argument_un, tok, try p.typeStr(operand.ty));
7138
7139 try operand.usualUnaryConversion(p, tok);
7140 if (operand.val.isArithmetic(p.comp)) {
7141 _ = try operand.val.sub(Value.zero, operand.val, operand.ty, p.comp);
7142 } else {
7143 operand.val = .{};
7144 }
7145 try operand.un(p, .negate_expr, tok);
7146 return operand;
7147 },
7148 .plus_plus => {
7149 p.tok_i += 1;
7150
7151 var operand = try p.castExpr();
7152 try operand.expect(p);
7153 if (!operand.ty.isScalar())
7154 try p.errStr(.invalid_argument_un, tok, try p.typeStr(operand.ty));
7155 if (operand.ty.isComplex())
7156 try p.errStr(.complex_prefix_postfix_op, p.tok_i, try p.typeStr(operand.ty));
7157
7158 if (!p.tmpTree().isLval(operand.node) or operand.ty.isConst()) {
7159 try p.errTok(.not_assignable, tok);
7160 return error.ParsingFailed;
7161 }
7162 try operand.usualUnaryConversion(p, tok);
7163
7164 if (operand.val.is(.int, p.comp) or operand.val.is(.int, p.comp)) {
7165 if (try operand.val.add(operand.val, Value.one, operand.ty, p.comp))
7166 try p.errOverflow(tok, operand);
7167 } else {
7168 operand.val = .{};
7169 }
7170
7171 try operand.un(p, .pre_inc_expr, tok);
7172 return operand;
7173 },
7174 .minus_minus => {
7175 p.tok_i += 1;
7176
7177 var operand = try p.castExpr();
7178 try operand.expect(p);
7179 if (!operand.ty.isScalar())
7180 try p.errStr(.invalid_argument_un, tok, try p.typeStr(operand.ty));
7181 if (operand.ty.isComplex())
7182 try p.errStr(.complex_prefix_postfix_op, p.tok_i, try p.typeStr(operand.ty));
7183
7184 if (!p.tmpTree().isLval(operand.node) or operand.ty.isConst()) {
7185 try p.errTok(.not_assignable, tok);
7186 return error.ParsingFailed;
7187 }
7188 try operand.usualUnaryConversion(p, tok);
7189
7190 if (operand.val.is(.int, p.comp) or operand.val.is(.int, p.comp)) {
7191 if (try operand.val.sub(operand.val, Value.one, operand.ty, p.comp))
7192 try p.errOverflow(tok, operand);
7193 } else {
7194 operand.val = .{};
7195 }
7196
7197 try operand.un(p, .pre_dec_expr, tok);
7198 return operand;
7199 },
7200 .tilde => {
7201 p.tok_i += 1;
7202
7203 var operand = try p.castExpr();
7204 try operand.expect(p);
7205 try operand.lvalConversion(p);
7206 try operand.usualUnaryConversion(p, tok);
7207 if (operand.ty.isInt()) {
7208 if (operand.val.is(.int, p.comp)) {
7209 operand.val = try operand.val.bitNot(operand.ty, p.comp);
7210 }
7211 } else if (operand.ty.isComplex()) {
7212 try p.errStr(.complex_conj, tok, try p.typeStr(operand.ty));
7213 if (operand.val.is(.complex, p.comp)) {
7214 operand.val = try operand.val.complexConj(operand.ty, p.comp);
7215 }
7216 } else {
7217 try p.errStr(.invalid_argument_un, tok, try p.typeStr(operand.ty));
7218 operand.val = .{};
7219 }
7220 try operand.un(p, .bit_not_expr, tok);
7221 return operand;
7222 },
7223 .bang => {
7224 p.tok_i += 1;
7225
7226 var operand = try p.castExpr();
7227 try operand.expect(p);
7228 try operand.lvalConversion(p);
7229 if (!operand.ty.isScalar())
7230 try p.errStr(.invalid_argument_un, tok, try p.typeStr(operand.ty));
7231
7232 try operand.usualUnaryConversion(p, tok);
7233 if (operand.val.is(.int, p.comp)) {
7234 operand.val = Value.fromBool(!operand.val.toBool(p.comp));
7235 } else if (operand.val.opt_ref == .null) {
7236 operand.val = Value.one;
7237 } else {
7238 if (operand.ty.isDecayed()) {
7239 operand.val = Value.zero;
7240 } else {
7241 operand.val = .{};
7242 }
7243 }
7244 operand.ty = .{ .specifier = .int };
7245 try operand.un(p, .bool_not_expr, tok);
7246 return operand;
7247 },
7248 .keyword_sizeof => {
7249 p.tok_i += 1;
7250 const expected_paren = p.tok_i;
7251 var res = Result{};
7252 if (try p.typeName()) |ty| {
7253 res.ty = ty;
7254 try p.errTok(.expected_parens_around_typename, expected_paren);
7255 } else if (p.eatToken(.l_paren)) |l_paren| {
7256 if (try p.typeName()) |ty| {
7257 res.ty = ty;
7258 try p.expectClosing(l_paren, .r_paren);
7259 } else {
7260 p.tok_i = expected_paren;
7261 res = try p.parseNoEval(unExpr);
7262 }
7263 } else {
7264 res = try p.parseNoEval(unExpr);
7265 }
7266
7267 if (res.ty.is(.void)) {
7268 try p.errStr(.pointer_arith_void, tok, "sizeof");
7269 } else if (res.ty.isDecayed()) {
7270 const array_ty = res.ty.originalTypeOfDecayedArray();
7271 const err_str = try p.typePairStrExtra(res.ty, " instead of ", array_ty);
7272 try p.errStr(.sizeof_array_arg, tok, err_str);
7273 }
7274 if (res.ty.sizeof(p.comp)) |size| {
7275 if (size == 0) {
7276 try p.errTok(.sizeof_returns_zero, tok);
7277 }
7278 res.val = try Value.int(size, p.comp);
7279 res.ty = p.comp.types.size;
7280 } else {
7281 res.val = .{};
7282 if (res.ty.hasIncompleteSize()) {
7283 try p.errStr(.invalid_sizeof, expected_paren - 1, try p.typeStr(res.ty));
7284 res.ty = Type.invalid;
7285 } else {
7286 res.ty = p.comp.types.size;
7287 }
7288 }
7289 try res.un(p, .sizeof_expr, tok);
7290 return res;
7291 },
7292 .keyword_alignof,
7293 .keyword_alignof1,
7294 .keyword_alignof2,
7295 .keyword_c23_alignof,
7296 => {
7297 p.tok_i += 1;
7298 const expected_paren = p.tok_i;
7299 var res = Result{};
7300 if (try p.typeName()) |ty| {
7301 res.ty = ty;
7302 try p.errTok(.expected_parens_around_typename, expected_paren);
7303 } else if (p.eatToken(.l_paren)) |l_paren| {
7304 if (try p.typeName()) |ty| {
7305 res.ty = ty;
7306 try p.expectClosing(l_paren, .r_paren);
7307 } else {
7308 p.tok_i = expected_paren;
7309 res = try p.parseNoEval(unExpr);
7310 try p.errTok(.alignof_expr, expected_paren);
7311 }
7312 } else {
7313 res = try p.parseNoEval(unExpr);
7314 try p.errTok(.alignof_expr, expected_paren);
7315 }
7316
7317 if (res.ty.is(.void)) {
7318 try p.errStr(.pointer_arith_void, tok, "alignof");
7319 }
7320 if (res.ty.alignable()) {
7321 res.val = try Value.int(res.ty.alignof(p.comp), p.comp);
7322 res.ty = p.comp.types.size;
7323 } else {
7324 try p.errStr(.invalid_alignof, expected_paren, try p.typeStr(res.ty));
7325 res.ty = Type.invalid;
7326 }
7327 try res.un(p, .alignof_expr, tok);
7328 return res;
7329 },
7330 .keyword_extension => {
7331 p.tok_i += 1;
7332 const saved_extension = p.extension_suppressed;
7333 defer p.extension_suppressed = saved_extension;
7334 p.extension_suppressed = true;
7335
7336 var child = try p.castExpr();
7337 try child.expect(p);
7338 return child;
7339 },
7340 .keyword_imag1, .keyword_imag2 => {
7341 const imag_tok = p.tok_i;
7342 p.tok_i += 1;
7343
7344 var operand = try p.castExpr();
7345 try operand.expect(p);
7346 try operand.lvalConversion(p);
7347 if (operand.ty.is(.invalid)) return Result.invalid;
7348 if (!operand.ty.isInt() and !operand.ty.isFloat()) {
7349 try p.errStr(.invalid_imag, imag_tok, try p.typeStr(operand.ty));
7350 }
7351 if (operand.ty.isComplex()) {
7352 operand.val = try operand.val.imaginaryPart(p.comp);
7353 } else if (operand.ty.isReal()) {
7354 switch (p.comp.langopts.emulate) {
7355 .msvc => {}, // Doesn't support `_Complex` or `__imag` in the first place
7356 .gcc => operand.val = Value.zero,
7357 .clang => {
7358 if (operand.val.is(.int, p.comp) or operand.val.is(.float, p.comp)) {
7359 operand.val = Value.zero;
7360 } else {
7361 operand.val = .{};
7362 }
7363 },
7364 }
7365 }
7366 // convert _Complex T to T
7367 operand.ty = operand.ty.makeReal();
7368 try operand.un(p, .imag_expr, tok);
7369 return operand;
7370 },
7371 .keyword_real1, .keyword_real2 => {
7372 const real_tok = p.tok_i;
7373 p.tok_i += 1;
7374
7375 var operand = try p.castExpr();
7376 try operand.expect(p);
7377 try operand.lvalConversion(p);
7378 if (operand.ty.is(.invalid)) return Result.invalid;
7379 if (!operand.ty.isInt() and !operand.ty.isFloat()) {
7380 try p.errStr(.invalid_real, real_tok, try p.typeStr(operand.ty));
7381 }
7382 // convert _Complex T to T
7383 operand.ty = operand.ty.makeReal();
7384 operand.val = try operand.val.realPart(p.comp);
7385 try operand.un(p, .real_expr, tok);
7386 return operand;
7387 },
7388 else => {
7389 var lhs = try p.compoundLiteral();
7390 if (lhs.empty(p)) {
7391 lhs = try p.primaryExpr();
7392 if (lhs.empty(p)) return lhs;
7393 }
7394 while (true) {
7395 const suffix = try p.suffixExpr(lhs);
7396 if (suffix.empty(p)) break;
7397 lhs = suffix;
7398 }
7399 return lhs;
7400 },
7401 }
7402}
7403
7404/// compoundLiteral
7405/// : '(' storageClassSpec* type_name ')' '{' initializer_list '}'
7406/// | '(' storageClassSpec* type_name ')' '{' initializer_list ',' '}'
7407fn compoundLiteral(p: *Parser) Error!Result {
7408 const l_paren = p.eatToken(.l_paren) orelse return Result{};
7409
7410 var d: DeclSpec = .{ .ty = .{ .specifier = undefined } };
7411 const any = if (p.comp.langopts.standard.atLeast(.c23))
7412 try p.storageClassSpec(&d)
7413 else
7414 false;
7415
7416 const tag: Tree.Tag = switch (d.storage_class) {
7417 .static => if (d.thread_local != null)
7418 .static_thread_local_compound_literal_expr
7419 else
7420 .static_compound_literal_expr,
7421 .register, .none => if (d.thread_local != null)
7422 .thread_local_compound_literal_expr
7423 else
7424 .compound_literal_expr,
7425 .auto, .@"extern", .typedef => |tok| blk: {
7426 try p.errStr(.invalid_compound_literal_storage_class, tok, @tagName(d.storage_class));
7427 d.storage_class = .none;
7428 break :blk if (d.thread_local != null)
7429 .thread_local_compound_literal_expr
7430 else
7431 .compound_literal_expr;
7432 },
7433 };
7434
7435 var ty = (try p.typeName()) orelse {
7436 p.tok_i = l_paren;
7437 if (any) {
7438 try p.err(.expected_type);
7439 return error.ParsingFailed;
7440 }
7441 return Result{};
7442 };
7443 if (d.storage_class == .register) ty.qual.register = true;
7444 try p.expectClosing(l_paren, .r_paren);
7445
7446 if (ty.isFunc()) {
7447 try p.err(.func_init);
7448 } else if (ty.is(.variable_len_array)) {
7449 try p.err(.vla_init);
7450 } else if (ty.hasIncompleteSize() and !ty.is(.incomplete_array)) {
7451 try p.errStr(.variable_incomplete_ty, p.tok_i, try p.typeStr(ty));
7452 return error.ParsingFailed;
7453 }
7454 var init_list_expr = try p.initializer(ty);
7455 if (d.constexpr) |_| {
7456 // TODO error if not constexpr
7457 }
7458 try init_list_expr.un(p, tag, l_paren);
7459 return init_list_expr;
7460}
7461
7462/// suffixExpr
7463/// : '[' expr ']'
7464/// | '(' argumentExprList? ')'
7465/// | '.' IDENTIFIER
7466/// | '->' IDENTIFIER
7467/// | '++'
7468/// | '--'
7469/// argumentExprList : assignExpr (',' assignExpr)*
7470fn suffixExpr(p: *Parser, lhs: Result) Error!Result {
7471 assert(!lhs.empty(p));
7472 switch (p.tok_ids[p.tok_i]) {
7473 .l_paren => return p.callExpr(lhs),
7474 .plus_plus => {
7475 defer p.tok_i += 1;
7476
7477 var operand = lhs;
7478 if (!operand.ty.isScalar())
7479 try p.errStr(.invalid_argument_un, p.tok_i, try p.typeStr(operand.ty));
7480 if (operand.ty.isComplex())
7481 try p.errStr(.complex_prefix_postfix_op, p.tok_i, try p.typeStr(operand.ty));
7482
7483 if (!p.tmpTree().isLval(operand.node) or operand.ty.isConst()) {
7484 try p.err(.not_assignable);
7485 return error.ParsingFailed;
7486 }
7487 try operand.usualUnaryConversion(p, p.tok_i);
7488
7489 try operand.un(p, .post_inc_expr, p.tok_i);
7490 return operand;
7491 },
7492 .minus_minus => {
7493 defer p.tok_i += 1;
7494
7495 var operand = lhs;
7496 if (!operand.ty.isScalar())
7497 try p.errStr(.invalid_argument_un, p.tok_i, try p.typeStr(operand.ty));
7498 if (operand.ty.isComplex())
7499 try p.errStr(.complex_prefix_postfix_op, p.tok_i, try p.typeStr(operand.ty));
7500
7501 if (!p.tmpTree().isLval(operand.node) or operand.ty.isConst()) {
7502 try p.err(.not_assignable);
7503 return error.ParsingFailed;
7504 }
7505 try operand.usualUnaryConversion(p, p.tok_i);
7506
7507 try operand.un(p, .post_dec_expr, p.tok_i);
7508 return operand;
7509 },
7510 .l_bracket => {
7511 const l_bracket = p.tok_i;
7512 p.tok_i += 1;
7513 var index = try p.expr();
7514 try index.expect(p);
7515 try p.expectClosing(l_bracket, .r_bracket);
7516
7517 const array_before_conversion = lhs;
7518 const index_before_conversion = index;
7519 var ptr = lhs;
7520 try ptr.lvalConversion(p);
7521 try index.lvalConversion(p);
7522 if (ptr.ty.isPtr()) {
7523 ptr.ty = ptr.ty.elemType();
7524 if (index.ty.isInt()) {
7525 try p.checkArrayBounds(index_before_conversion, array_before_conversion, l_bracket);
7526 } else {
7527 try p.errTok(.invalid_index, l_bracket);
7528 }
7529 } else if (index.ty.isPtr()) {
7530 index.ty = index.ty.elemType();
7531 if (ptr.ty.isInt()) {
7532 try p.checkArrayBounds(array_before_conversion, index_before_conversion, l_bracket);
7533 } else {
7534 try p.errTok(.invalid_index, l_bracket);
7535 }
7536 std.mem.swap(Result, &ptr, &index);
7537 } else {
7538 try p.errTok(.invalid_subscript, l_bracket);
7539 }
7540
7541 try ptr.saveValue(p);
7542 try index.saveValue(p);
7543 try ptr.bin(p, .array_access_expr, index, l_bracket);
7544 return ptr;
7545 },
7546 .period => {
7547 p.tok_i += 1;
7548 const name = try p.expectIdentifier();
7549 return p.fieldAccess(lhs, name, false);
7550 },
7551 .arrow => {
7552 p.tok_i += 1;
7553 const name = try p.expectIdentifier();
7554 if (lhs.ty.isArray()) {
7555 var copy = lhs;
7556 copy.ty.decayArray();
7557 try copy.implicitCast(p, .array_to_pointer);
7558 return p.fieldAccess(copy, name, true);
7559 }
7560 return p.fieldAccess(lhs, name, true);
7561 },
7562 else => return Result{},
7563 }
7564}
7565
7566fn fieldAccess(
7567 p: *Parser,
7568 lhs: Result,
7569 field_name_tok: TokenIndex,
7570 is_arrow: bool,
7571) !Result {
7572 const expr_ty = lhs.ty;
7573 const is_ptr = expr_ty.isPtr();
7574 const expr_base_ty = if (is_ptr) expr_ty.elemType() else expr_ty;
7575 const record_ty = expr_base_ty.getRecord() orelse {
7576 try p.errStr(.expected_record_ty, field_name_tok, try p.typeStr(expr_ty));
7577 return error.ParsingFailed;
7578 };
7579
7580 if (record_ty.isIncomplete()) {
7581 try p.errStr(.deref_incomplete_ty_ptr, field_name_tok - 2, try p.typeStr(expr_base_ty));
7582 return error.ParsingFailed;
7583 }
7584 if (is_arrow and !is_ptr) try p.errStr(.member_expr_not_ptr, field_name_tok, try p.typeStr(expr_ty));
7585 if (!is_arrow and is_ptr) try p.errStr(.member_expr_ptr, field_name_tok, try p.typeStr(expr_ty));
7586
7587 const field_name = try StrInt.intern(p.comp, p.tokSlice(field_name_tok));
7588 try p.validateFieldAccess(record_ty, expr_ty, field_name_tok, field_name);
7589 var discard: u64 = 0;
7590 return p.fieldAccessExtra(lhs.node, record_ty, field_name, is_arrow, &discard);
7591}
7592
7593fn validateFieldAccess(p: *Parser, record_ty: *const Type.Record, expr_ty: Type, field_name_tok: TokenIndex, field_name: StringId) Error!void {
7594 if (record_ty.hasField(field_name)) return;
7595
7596 p.strings.items.len = 0;
7597
7598 try p.strings.writer().print("'{s}' in '", .{p.tokSlice(field_name_tok)});
7599 const mapper = p.comp.string_interner.getSlowTypeMapper();
7600 try expr_ty.print(mapper, p.comp.langopts, p.strings.writer());
7601 try p.strings.append('\'');
7602
7603 const duped = try p.comp.diagnostics.arena.allocator().dupe(u8, p.strings.items);
7604 try p.errStr(.no_such_member, field_name_tok, duped);
7605 return error.ParsingFailed;
7606}
7607
7608fn fieldAccessExtra(p: *Parser, lhs: NodeIndex, record_ty: *const Type.Record, field_name: StringId, is_arrow: bool, offset_bits: *u64) Error!Result {
7609 for (record_ty.fields, 0..) |f, i| {
7610 if (f.isAnonymousRecord()) {
7611 if (!f.ty.hasField(field_name)) continue;
7612 const inner = try p.addNode(.{
7613 .tag = if (is_arrow) .member_access_ptr_expr else .member_access_expr,
7614 .ty = f.ty,
7615 .data = .{ .member = .{ .lhs = lhs, .index = @intCast(i) } },
7616 });
7617 const ret = p.fieldAccessExtra(inner, f.ty.getRecord().?, field_name, false, offset_bits);
7618 offset_bits.* = f.layout.offset_bits;
7619 return ret;
7620 }
7621 if (field_name == f.name) {
7622 offset_bits.* = f.layout.offset_bits;
7623 return Result{
7624 .ty = f.ty,
7625 .node = try p.addNode(.{
7626 .tag = if (is_arrow) .member_access_ptr_expr else .member_access_expr,
7627 .ty = f.ty,
7628 .data = .{ .member = .{ .lhs = lhs, .index = @intCast(i) } },
7629 }),
7630 };
7631 }
7632 }
7633 // We already checked that this container has a field by the name.
7634 unreachable;
7635}
7636
7637fn checkVaStartArg(p: *Parser, builtin_tok: TokenIndex, first_after: TokenIndex, param_tok: TokenIndex, arg: *Result, idx: u32) !void {
7638 assert(idx != 0);
7639 if (idx > 1) {
7640 try p.errTok(.closing_paren, first_after);
7641 return error.ParsingFailed;
7642 }
7643
7644 var func_ty = p.func.ty orelse {
7645 try p.errTok(.va_start_not_in_func, builtin_tok);
7646 return;
7647 };
7648 const func_params = func_ty.params();
7649 if (func_ty.specifier != .var_args_func or func_params.len == 0) {
7650 return p.errTok(.va_start_fixed_args, builtin_tok);
7651 }
7652 const last_param_name = func_params[func_params.len - 1].name;
7653 const decl_ref = p.getNode(arg.node, .decl_ref_expr);
7654 if (decl_ref == null or last_param_name != try StrInt.intern(p.comp, p.tokSlice(p.nodes.items(.data)[@intFromEnum(decl_ref.?)].decl_ref))) {
7655 try p.errTok(.va_start_not_last_param, param_tok);
7656 }
7657}
7658
7659fn checkArithOverflowArg(p: *Parser, builtin_tok: TokenIndex, first_after: TokenIndex, param_tok: TokenIndex, arg: *Result, idx: u32) !void {
7660 _ = builtin_tok;
7661 _ = first_after;
7662 if (idx <= 1) {
7663 if (!arg.ty.isInt()) {
7664 return p.errStr(.overflow_builtin_requires_int, param_tok, try p.typeStr(arg.ty));
7665 }
7666 } else if (idx == 2) {
7667 if (!arg.ty.isPtr()) return p.errStr(.overflow_result_requires_ptr, param_tok, try p.typeStr(arg.ty));
7668 const child = arg.ty.elemType();
7669 if (!child.isInt() or child.is(.bool) or child.is(.@"enum") or child.qual.@"const") return p.errStr(.overflow_result_requires_ptr, param_tok, try p.typeStr(arg.ty));
7670 }
7671}
7672
7673fn checkComplexArg(p: *Parser, builtin_tok: TokenIndex, first_after: TokenIndex, param_tok: TokenIndex, arg: *Result, idx: u32) !void {
7674 _ = builtin_tok;
7675 _ = first_after;
7676 if (idx <= 1 and !arg.ty.isFloat()) {
7677 try p.errStr(.not_floating_type, param_tok, try p.typeStr(arg.ty));
7678 } else if (idx == 1) {
7679 const prev_idx = p.list_buf.items[p.list_buf.items.len - 1];
7680 const prev_ty = p.nodes.items(.ty)[@intFromEnum(prev_idx)];
7681 if (!prev_ty.eql(arg.ty, p.comp, false)) {
7682 try p.errStr(.argument_types_differ, param_tok, try p.typePairStrExtra(prev_ty, " vs ", arg.ty));
7683 }
7684 }
7685}
7686
7687fn callExpr(p: *Parser, lhs: Result) Error!Result {
7688 const l_paren = p.tok_i;
7689 p.tok_i += 1;
7690 const ty = lhs.ty.isCallable() orelse {
7691 try p.errStr(.not_callable, l_paren, try p.typeStr(lhs.ty));
7692 return error.ParsingFailed;
7693 };
7694 const params = ty.params();
7695 var func = lhs;
7696 try func.lvalConversion(p);
7697
7698 const list_buf_top = p.list_buf.items.len;
7699 defer p.list_buf.items.len = list_buf_top;
7700 try p.list_buf.append(func.node);
7701 var arg_count: u32 = 0;
7702 var first_after = l_paren;
7703
7704 const call_expr = CallExpr.init(p, lhs.node, func.node);
7705
7706 while (p.eatToken(.r_paren) == null) {
7707 const param_tok = p.tok_i;
7708 if (arg_count == params.len) first_after = p.tok_i;
7709 var arg = try p.assignExpr();
7710 try arg.expect(p);
7711
7712 if (call_expr.shouldPerformLvalConversion(arg_count)) {
7713 try arg.lvalConversion(p);
7714 }
7715 if (arg.ty.hasIncompleteSize() and !arg.ty.is(.void)) return error.ParsingFailed;
7716
7717 if (arg_count >= params.len) {
7718 if (call_expr.shouldPromoteVarArg(arg_count)) {
7719 if (arg.ty.isInt()) try arg.intCast(p, arg.ty.integerPromotion(p.comp), param_tok);
7720 if (arg.ty.is(.float)) try arg.floatCast(p, .{ .specifier = .double });
7721 }
7722 try call_expr.checkVarArg(p, first_after, param_tok, &arg, arg_count);
7723 try arg.saveValue(p);
7724 try p.list_buf.append(arg.node);
7725 arg_count += 1;
7726
7727 _ = p.eatToken(.comma) orelse {
7728 try p.expectClosing(l_paren, .r_paren);
7729 break;
7730 };
7731 continue;
7732 }
7733 const p_ty = params[arg_count].ty;
7734 if (p_ty.specifier == .static_array) {
7735 const arg_array_len: u64 = arg.ty.arrayLen() orelse std.math.maxInt(u64);
7736 const param_array_len: u64 = p_ty.arrayLen().?;
7737 if (arg_array_len < param_array_len) {
7738 const extra = Diagnostics.Message.Extra{ .arguments = .{
7739 .expected = @intCast(arg_array_len),
7740 .actual = @intCast(param_array_len),
7741 } };
7742 try p.errExtra(.array_argument_too_small, param_tok, extra);
7743 try p.errTok(.callee_with_static_array, params[arg_count].name_tok);
7744 }
7745 if (arg.val.isZero(p.comp)) {
7746 try p.errTok(.non_null_argument, param_tok);
7747 try p.errTok(.callee_with_static_array, params[arg_count].name_tok);
7748 }
7749 }
7750
7751 if (call_expr.shouldCoerceArg(arg_count)) {
7752 try arg.coerce(p, p_ty, param_tok, .{ .arg = params[arg_count].name_tok });
7753 }
7754 try arg.saveValue(p);
7755 try p.list_buf.append(arg.node);
7756 arg_count += 1;
7757
7758 _ = p.eatToken(.comma) orelse {
7759 try p.expectClosing(l_paren, .r_paren);
7760 break;
7761 };
7762 }
7763
7764 const actual: u32 = @intCast(arg_count);
7765 const extra = Diagnostics.Message.Extra{ .arguments = .{
7766 .expected = @intCast(params.len),
7767 .actual = actual,
7768 } };
7769 if (call_expr.paramCountOverride()) |expected| {
7770 if (expected != actual) {
7771 try p.errExtra(.expected_arguments, first_after, .{ .arguments = .{ .expected = expected, .actual = actual } });
7772 }
7773 } else if (ty.is(.func) and params.len != arg_count) {
7774 try p.errExtra(.expected_arguments, first_after, extra);
7775 } else if (ty.is(.old_style_func) and params.len != arg_count) {
7776 if (params.len == 0)
7777 try p.errTok(.passing_args_to_kr, first_after)
7778 else
7779 try p.errExtra(.expected_arguments_old, first_after, extra);
7780 } else if (ty.is(.var_args_func) and arg_count < params.len) {
7781 try p.errExtra(.expected_at_least_arguments, first_after, extra);
7782 }
7783
7784 return call_expr.finish(p, ty, list_buf_top, arg_count);
7785}
7786
7787fn checkArrayBounds(p: *Parser, index: Result, array: Result, tok: TokenIndex) !void {
7788 if (index.val.opt_ref == .none) return;
7789
7790 const array_len = array.ty.arrayLen() orelse return;
7791 if (array_len == 0) return;
7792
7793 if (array_len == 1) {
7794 if (p.getNode(array.node, .member_access_expr) orelse p.getNode(array.node, .member_access_ptr_expr)) |node| {
7795 const data = p.nodes.items(.data)[@intFromEnum(node)];
7796 var lhs = p.nodes.items(.ty)[@intFromEnum(data.member.lhs)];
7797 if (lhs.get(.pointer)) |ptr| {
7798 lhs = ptr.data.sub_type.*;
7799 }
7800 if (lhs.is(.@"struct")) {
7801 const record = lhs.getRecord().?;
7802 if (data.member.index + 1 == record.fields.len) {
7803 if (!index.val.isZero(p.comp)) {
7804 try p.errStr(.old_style_flexible_struct, tok, try index.str(p));
7805 }
7806 return;
7807 }
7808 }
7809 }
7810 }
7811 const index_int = index.val.toInt(u64, p.comp) orelse std.math.maxInt(u64);
7812 if (index.ty.isUnsignedInt(p.comp)) {
7813 if (index_int >= array_len) {
7814 try p.errStr(.array_after, tok, try index.str(p));
7815 }
7816 } else {
7817 if (index.val.compare(.lt, Value.zero, p.comp)) {
7818 try p.errStr(.array_before, tok, try index.str(p));
7819 } else if (index_int >= array_len) {
7820 try p.errStr(.array_after, tok, try index.str(p));
7821 }
7822 }
7823}
7824
7825/// primaryExpr
7826/// : IDENTIFIER
7827/// | keyword_true
7828/// | keyword_false
7829/// | keyword_nullptr
7830/// | INTEGER_LITERAL
7831/// | FLOAT_LITERAL
7832/// | IMAGINARY_LITERAL
7833/// | CHAR_LITERAL
7834/// | STRING_LITERAL
7835/// | '(' expr ')'
7836/// | genericSelection
7837fn primaryExpr(p: *Parser) Error!Result {
7838 if (p.eatToken(.l_paren)) |l_paren| {
7839 var e = try p.expr();
7840 try e.expect(p);
7841 try p.expectClosing(l_paren, .r_paren);
7842 try e.un(p, .paren_expr, l_paren);
7843 return e;
7844 }
7845 switch (p.tok_ids[p.tok_i]) {
7846 .identifier, .extended_identifier => {
7847 const name_tok = try p.expectIdentifier();
7848 const name = p.tokSlice(name_tok);
7849 const interned_name = try StrInt.intern(p.comp, name);
7850 if (interned_name == p.auto_type_decl_name) {
7851 try p.errStr(.auto_type_self_initialized, name_tok, name);
7852 return error.ParsingFailed;
7853 }
7854 if (p.syms.findSymbol(interned_name)) |sym| {
7855 try p.checkDeprecatedUnavailable(sym.ty, name_tok, sym.tok);
7856 if (sym.kind == .constexpr) {
7857 return Result{
7858 .val = sym.val,
7859 .ty = sym.ty,
7860 .node = try p.addNode(.{
7861 .tag = .decl_ref_expr,
7862 .ty = sym.ty,
7863 .data = .{ .decl_ref = name_tok },
7864 .loc = @enumFromInt(name_tok),
7865 }),
7866 };
7867 }
7868 if (sym.val.is(.int, p.comp)) {
7869 switch (p.const_decl_folding) {
7870 .gnu_folding_extension => try p.errTok(.const_decl_folded, name_tok),
7871 .gnu_vla_folding_extension => try p.errTok(.const_decl_folded_vla, name_tok),
7872 else => {},
7873 }
7874 }
7875 return Result{
7876 .val = if (p.const_decl_folding == .no_const_decl_folding and sym.kind != .enumeration) Value{} else sym.val,
7877 .ty = sym.ty,
7878 .node = try p.addNode(.{
7879 .tag = if (sym.kind == .enumeration) .enumeration_ref else .decl_ref_expr,
7880 .ty = sym.ty,
7881 .data = .{ .decl_ref = name_tok },
7882 .loc = @enumFromInt(name_tok),
7883 }),
7884 };
7885 }
7886 if (try p.comp.builtins.getOrCreate(p.comp, name, p.arena)) |some| {
7887 for (p.tok_ids[p.tok_i..]) |id| switch (id) {
7888 .r_paren => {}, // closing grouped expr
7889 .l_paren => break, // beginning of a call
7890 else => {
7891 try p.errTok(.builtin_must_be_called, name_tok);
7892 return error.ParsingFailed;
7893 },
7894 };
7895 if (some.builtin.properties.header != .none) {
7896 try p.errStr(.implicit_builtin, name_tok, name);
7897 try p.errExtra(.implicit_builtin_header_note, name_tok, .{ .builtin_with_header = .{
7898 .builtin = some.builtin.tag,
7899 .header = some.builtin.properties.header,
7900 } });
7901 }
7902
7903 return Result{
7904 .ty = some.ty,
7905 .node = try p.addNode(.{
7906 .tag = .builtin_call_expr_one,
7907 .ty = some.ty,
7908 .data = .{ .decl = .{ .name = name_tok, .node = .none } },
7909 .loc = @enumFromInt(name_tok),
7910 }),
7911 };
7912 }
7913 if (p.tok_ids[p.tok_i] == .l_paren and !p.comp.langopts.standard.atLeast(.c23)) {
7914 // allow implicitly declaring functions before C99 like `puts("foo")`
7915 if (mem.startsWith(u8, name, "__builtin_"))
7916 try p.errStr(.unknown_builtin, name_tok, name)
7917 else
7918 try p.errStr(.implicit_func_decl, name_tok, name);
7919
7920 const func_ty = try p.arena.create(Type.Func);
7921 func_ty.* = .{ .return_type = .{ .specifier = .int }, .params = &.{} };
7922 const ty: Type = .{ .specifier = .old_style_func, .data = .{ .func = func_ty } };
7923 const node = try p.addNode(.{
7924 .ty = ty,
7925 .tag = .fn_proto,
7926 .data = .{ .decl = .{ .name = name_tok } },
7927 .loc = @enumFromInt(name_tok),
7928 });
7929
7930 try p.decl_buf.append(node);
7931 try p.syms.declareSymbol(p, interned_name, ty, name_tok, node);
7932
7933 return Result{
7934 .ty = ty,
7935 .node = try p.addNode(.{
7936 .tag = .decl_ref_expr,
7937 .ty = ty,
7938 .data = .{ .decl_ref = name_tok },
7939 .loc = @enumFromInt(name_tok),
7940 }),
7941 };
7942 }
7943 try p.errStr(.undeclared_identifier, name_tok, p.tokSlice(name_tok));
7944 return error.ParsingFailed;
7945 },
7946 .keyword_true, .keyword_false => |id| {
7947 const tok_i = p.tok_i;
7948 p.tok_i += 1;
7949 const res = Result{
7950 .val = Value.fromBool(id == .keyword_true),
7951 .ty = .{ .specifier = .bool },
7952 .node = try p.addNode(.{ .tag = .bool_literal, .ty = .{ .specifier = .bool }, .data = undefined, .loc = @enumFromInt(tok_i) }),
7953 };
7954 std.debug.assert(!p.in_macro); // Should have been replaced with .one / .zero
7955 try p.value_map.put(res.node, res.val);
7956 return res;
7957 },
7958 .keyword_nullptr => {
7959 defer p.tok_i += 1;
7960 try p.errStr(.pre_c23_compat, p.tok_i, "'nullptr'");
7961 return Result{
7962 .val = Value.null,
7963 .ty = .{ .specifier = .nullptr_t },
7964 .node = try p.addNode(.{
7965 .tag = .nullptr_literal,
7966 .ty = .{ .specifier = .nullptr_t },
7967 .data = undefined,
7968 .loc = @enumFromInt(p.tok_i),
7969 }),
7970 };
7971 },
7972 .macro_func, .macro_function => {
7973 defer p.tok_i += 1;
7974 var ty: Type = undefined;
7975 var tok = p.tok_i;
7976 if (p.func.ident) |some| {
7977 ty = some.ty;
7978 tok = p.nodes.items(.data)[@intFromEnum(some.node)].decl.name;
7979 } else if (p.func.ty) |_| {
7980 const strings_top = p.strings.items.len;
7981 defer p.strings.items.len = strings_top;
7982
7983 try p.strings.appendSlice(p.tokSlice(p.func.name));
7984 try p.strings.append(0);
7985 const predef = try p.makePredefinedIdentifier(strings_top);
7986 ty = predef.ty;
7987 p.func.ident = predef;
7988 } else {
7989 const strings_top = p.strings.items.len;
7990 defer p.strings.items.len = strings_top;
7991
7992 try p.strings.append(0);
7993 const predef = try p.makePredefinedIdentifier(strings_top);
7994 ty = predef.ty;
7995 p.func.ident = predef;
7996 try p.decl_buf.append(predef.node);
7997 }
7998 if (p.func.ty == null) try p.err(.predefined_top_level);
7999 return Result{
8000 .ty = ty,
8001 .node = try p.addNode(.{
8002 .tag = .decl_ref_expr,
8003 .ty = ty,
8004 .data = .{ .decl_ref = tok },
8005 .loc = @enumFromInt(tok),
8006 }),
8007 };
8008 },
8009 .macro_pretty_func => {
8010 defer p.tok_i += 1;
8011 var ty: Type = undefined;
8012 if (p.func.pretty_ident) |some| {
8013 ty = some.ty;
8014 } else if (p.func.ty) |func_ty| {
8015 const strings_top = p.strings.items.len;
8016 defer p.strings.items.len = strings_top;
8017
8018 const mapper = p.comp.string_interner.getSlowTypeMapper();
8019 try Type.printNamed(func_ty, p.tokSlice(p.func.name), mapper, p.comp.langopts, p.strings.writer());
8020 try p.strings.append(0);
8021 const predef = try p.makePredefinedIdentifier(strings_top);
8022 ty = predef.ty;
8023 p.func.pretty_ident = predef;
8024 } else {
8025 const strings_top = p.strings.items.len;
8026 defer p.strings.items.len = strings_top;
8027
8028 try p.strings.appendSlice("top level\x00");
8029 const predef = try p.makePredefinedIdentifier(strings_top);
8030 ty = predef.ty;
8031 p.func.pretty_ident = predef;
8032 try p.decl_buf.append(predef.node);
8033 }
8034 if (p.func.ty == null) try p.err(.predefined_top_level);
8035 return Result{
8036 .ty = ty,
8037 .node = try p.addNode(.{
8038 .tag = .decl_ref_expr,
8039 .ty = ty,
8040 .data = .{ .decl_ref = p.tok_i },
8041 .loc = @enumFromInt(p.tok_i),
8042 }),
8043 };
8044 },
8045 .string_literal,
8046 .string_literal_utf_16,
8047 .string_literal_utf_8,
8048 .string_literal_utf_32,
8049 .string_literal_wide,
8050 .unterminated_string_literal,
8051 => return p.stringLiteral(),
8052 .char_literal,
8053 .char_literal_utf_8,
8054 .char_literal_utf_16,
8055 .char_literal_utf_32,
8056 .char_literal_wide,
8057 .empty_char_literal,
8058 .unterminated_char_literal,
8059 => return p.charLiteral(),
8060 .zero => {
8061 defer p.tok_i += 1;
8062 var res: Result = .{ .val = Value.zero, .ty = if (p.in_macro) p.comp.types.intmax else Type.int };
8063 res.node = try p.addNode(.{ .tag = .int_literal, .ty = res.ty, .data = undefined, .loc = @enumFromInt(p.tok_i) });
8064 if (!p.in_macro) try p.value_map.put(res.node, res.val);
8065 return res;
8066 },
8067 .one => {
8068 defer p.tok_i += 1;
8069 var res: Result = .{ .val = Value.one, .ty = if (p.in_macro) p.comp.types.intmax else Type.int };
8070 res.node = try p.addNode(.{ .tag = .int_literal, .ty = res.ty, .data = undefined, .loc = @enumFromInt(p.tok_i) });
8071 if (!p.in_macro) try p.value_map.put(res.node, res.val);
8072 return res;
8073 },
8074 .pp_num => return p.ppNum(),
8075 .embed_byte => {
8076 assert(!p.in_macro);
8077 const loc = p.pp.tokens.items(.loc)[p.tok_i];
8078 defer p.tok_i += 1;
8079 const buf = p.comp.getSource(.generated).buf[loc.byte_offset..];
8080 var byte: u8 = buf[0] - '0';
8081 for (buf[1..]) |c| {
8082 if (!std.ascii.isDigit(c)) break;
8083 byte *= 10;
8084 byte += c - '0';
8085 }
8086 var res: Result = .{ .val = try Value.int(byte, p.comp) };
8087 res.node = try p.addNode(.{ .tag = .int_literal, .ty = res.ty, .data = undefined, .loc = @enumFromInt(p.tok_i) });
8088 try p.value_map.put(res.node, res.val);
8089 return res;
8090 },
8091 .keyword_generic => return p.genericSelection(),
8092 else => return Result{},
8093 }
8094}
8095
8096fn makePredefinedIdentifier(p: *Parser, strings_top: usize) !Result {
8097 const end: u32 = @intCast(p.strings.items.len);
8098 const elem_ty: Type = .{ .specifier = .char, .qual = .{ .@"const" = true } };
8099 const arr_ty = try p.arena.create(Type.Array);
8100 arr_ty.* = .{ .elem = elem_ty, .len = end - strings_top };
8101 const ty: Type = .{ .specifier = .array, .data = .{ .array = arr_ty } };
8102
8103 const slice = p.strings.items[strings_top..];
8104 const val = try Value.intern(p.comp, .{ .bytes = slice });
8105
8106 const str_lit = try p.addNode(.{ .tag = .string_literal_expr, .ty = ty, .data = undefined, .loc = @enumFromInt(p.tok_i) });
8107 if (!p.in_macro) try p.value_map.put(str_lit, val);
8108
8109 return Result{ .ty = ty, .node = try p.addNode(.{
8110 .tag = .implicit_static_var,
8111 .ty = ty,
8112 .data = .{ .decl = .{ .name = p.tok_i, .node = str_lit } },
8113 .loc = @enumFromInt(p.tok_i),
8114 }) };
8115}
8116
8117fn stringLiteral(p: *Parser) Error!Result {
8118 const string_start = p.tok_i;
8119 var string_end = p.tok_i;
8120 var string_kind: text_literal.Kind = .char;
8121 while (text_literal.Kind.classify(p.tok_ids[string_end], .string_literal)) |next| : (string_end += 1) {
8122 string_kind = string_kind.concat(next) catch {
8123 try p.errTok(.unsupported_str_cat, string_end);
8124 while (p.tok_ids[p.tok_i].isStringLiteral()) : (p.tok_i += 1) {}
8125 return error.ParsingFailed;
8126 };
8127 if (string_kind == .unterminated) {
8128 try p.errTok(.unterminated_string_literal_error, string_end);
8129 p.tok_i = string_end + 1;
8130 return error.ParsingFailed;
8131 }
8132 }
8133 const count = string_end - p.tok_i;
8134 assert(count > 0);
8135
8136 const char_width = string_kind.charUnitSize(p.comp);
8137
8138 const strings_top = p.strings.items.len;
8139 defer p.strings.items.len = strings_top;
8140
8141 const literal_start = mem.alignForward(usize, strings_top, @intFromEnum(char_width));
8142 try p.strings.resize(literal_start);
8143
8144 while (p.tok_i < string_end) : (p.tok_i += 1) {
8145 const this_kind = text_literal.Kind.classify(p.tok_ids[p.tok_i], .string_literal).?;
8146 const slice = this_kind.contentSlice(p.tokSlice(p.tok_i));
8147 var char_literal_parser = text_literal.Parser.init(slice, this_kind, 0x10ffff, p.comp);
8148
8149 try p.strings.ensureUnusedCapacity((slice.len + 1) * @intFromEnum(char_width)); // +1 for null terminator
8150 while (char_literal_parser.next()) |item| switch (item) {
8151 .value => |v| {
8152 switch (char_width) {
8153 .@"1" => p.strings.appendAssumeCapacity(@intCast(v)),
8154 .@"2" => {
8155 const word: u16 = @intCast(v);
8156 p.strings.appendSliceAssumeCapacity(mem.asBytes(&word));
8157 },
8158 .@"4" => p.strings.appendSliceAssumeCapacity(mem.asBytes(&v)),
8159 }
8160 },
8161 .codepoint => |c| {
8162 switch (char_width) {
8163 .@"1" => {
8164 var buf: [4]u8 = undefined;
8165 const written = std.unicode.utf8Encode(c, &buf) catch unreachable;
8166 const encoded = buf[0..written];
8167 p.strings.appendSliceAssumeCapacity(encoded);
8168 },
8169 .@"2" => {
8170 var utf16_buf: [2]u16 = undefined;
8171 var utf8_buf: [4]u8 = undefined;
8172 const utf8_written = std.unicode.utf8Encode(c, &utf8_buf) catch unreachable;
8173 const utf16_written = std.unicode.utf8ToUtf16Le(&utf16_buf, utf8_buf[0..utf8_written]) catch unreachable;
8174 const bytes = std.mem.sliceAsBytes(utf16_buf[0..utf16_written]);
8175 p.strings.appendSliceAssumeCapacity(bytes);
8176 },
8177 .@"4" => {
8178 const val: u32 = c;
8179 p.strings.appendSliceAssumeCapacity(mem.asBytes(&val));
8180 },
8181 }
8182 },
8183 .improperly_encoded => |bytes| {
8184 if (count > 1) {
8185 try p.errTok(.illegal_char_encoding_error, p.tok_i);
8186 return error.ParsingFailed;
8187 }
8188 p.strings.appendSliceAssumeCapacity(bytes);
8189 },
8190 .utf8_text => |view| {
8191 switch (char_width) {
8192 .@"1" => p.strings.appendSliceAssumeCapacity(view.bytes),
8193 .@"2" => {
8194 const capacity_slice: []align(@alignOf(u16)) u8 = @alignCast(p.strings.allocatedSlice()[literal_start..]);
8195 const dest_len = std.mem.alignBackward(usize, capacity_slice.len, 2);
8196 const dest = std.mem.bytesAsSlice(u16, capacity_slice[0..dest_len]);
8197 const words_written = std.unicode.utf8ToUtf16Le(dest, view.bytes) catch unreachable;
8198 p.strings.resize(p.strings.items.len + words_written * 2) catch unreachable;
8199 },
8200 .@"4" => {
8201 var it = view.iterator();
8202 while (it.nextCodepoint()) |codepoint| {
8203 const val: u32 = codepoint;
8204 p.strings.appendSliceAssumeCapacity(mem.asBytes(&val));
8205 }
8206 },
8207 }
8208 },
8209 };
8210 for (char_literal_parser.errors()) |item| {
8211 try p.errExtra(item.tag, p.tok_i, item.extra);
8212 }
8213 }
8214 p.strings.appendNTimesAssumeCapacity(0, @intFromEnum(char_width));
8215 const slice = p.strings.items[literal_start..];
8216
8217 // TODO this won't do anything if there is a cache hit
8218 const interned_align = mem.alignForward(
8219 usize,
8220 p.comp.interner.strings.items.len,
8221 string_kind.internalStorageAlignment(p.comp),
8222 );
8223 try p.comp.interner.strings.resize(p.gpa, interned_align);
8224
8225 const val = try Value.intern(p.comp, .{ .bytes = slice });
8226
8227 const arr_ty = try p.arena.create(Type.Array);
8228 arr_ty.* = .{ .elem = string_kind.elementType(p.comp), .len = @divExact(slice.len, @intFromEnum(char_width)) };
8229 var res: Result = .{
8230 .ty = .{
8231 .specifier = .array,
8232 .data = .{ .array = arr_ty },
8233 },
8234 .val = val,
8235 };
8236 res.node = try p.addNode(.{ .tag = .string_literal_expr, .ty = res.ty, .data = undefined, .loc = @enumFromInt(string_start) });
8237 if (!p.in_macro) try p.value_map.put(res.node, res.val);
8238 return res;
8239}
8240
8241fn charLiteral(p: *Parser) Error!Result {
8242 defer p.tok_i += 1;
8243 const tok_id = p.tok_ids[p.tok_i];
8244 const char_kind = text_literal.Kind.classify(tok_id, .char_literal) orelse {
8245 if (tok_id == .empty_char_literal) {
8246 try p.err(.empty_char_literal_error);
8247 } else if (tok_id == .unterminated_char_literal) {
8248 try p.err(.unterminated_char_literal_error);
8249 } else unreachable;
8250 return .{
8251 .ty = Type.int,
8252 .val = Value.zero,
8253 .node = try p.addNode(.{ .tag = .char_literal, .ty = Type.int, .data = undefined, .loc = @enumFromInt(p.tok_i) }),
8254 };
8255 };
8256 if (char_kind == .utf_8) try p.err(.u8_char_lit);
8257 var val: u32 = 0;
8258
8259 const slice = char_kind.contentSlice(p.tokSlice(p.tok_i));
8260
8261 var is_multichar = false;
8262 if (slice.len == 1 and std.ascii.isASCII(slice[0])) {
8263 // fast path: single unescaped ASCII char
8264 val = slice[0];
8265 } else {
8266 const max_codepoint = char_kind.maxCodepoint(p.comp);
8267 var char_literal_parser = text_literal.Parser.init(slice, char_kind, max_codepoint, p.comp);
8268
8269 const max_chars_expected = 4;
8270 var stack_fallback = std.heap.stackFallback(max_chars_expected * @sizeOf(u32), p.comp.gpa);
8271 var chars = std.ArrayList(u32).initCapacity(stack_fallback.get(), max_chars_expected) catch unreachable; // stack allocation already succeeded
8272 defer chars.deinit();
8273
8274 while (char_literal_parser.next()) |item| switch (item) {
8275 .value => |v| try chars.append(v),
8276 .codepoint => |c| try chars.append(c),
8277 .improperly_encoded => |s| {
8278 try chars.ensureUnusedCapacity(s.len);
8279 for (s) |c| chars.appendAssumeCapacity(c);
8280 },
8281 .utf8_text => |view| {
8282 var it = view.iterator();
8283 var max_codepoint_seen: u21 = 0;
8284 try chars.ensureUnusedCapacity(view.bytes.len);
8285 while (it.nextCodepoint()) |c| {
8286 max_codepoint_seen = @max(max_codepoint_seen, c);
8287 chars.appendAssumeCapacity(c);
8288 }
8289 if (max_codepoint_seen > max_codepoint) {
8290 char_literal_parser.err(.char_too_large, .{ .none = {} });
8291 }
8292 },
8293 };
8294
8295 is_multichar = chars.items.len > 1;
8296 if (is_multichar) {
8297 if (char_kind == .char and chars.items.len == 4) {
8298 char_literal_parser.warn(.four_char_char_literal, .{ .none = {} });
8299 } else if (char_kind == .char) {
8300 char_literal_parser.warn(.multichar_literal_warning, .{ .none = {} });
8301 } else {
8302 const kind = switch (char_kind) {
8303 .wide => "wide",
8304 .utf_8, .utf_16, .utf_32 => "Unicode",
8305 else => unreachable,
8306 };
8307 char_literal_parser.err(.invalid_multichar_literal, .{ .str = kind });
8308 }
8309 }
8310
8311 var multichar_overflow = false;
8312 if (char_kind == .char and is_multichar) {
8313 for (chars.items) |item| {
8314 val, const overflowed = @shlWithOverflow(val, 8);
8315 multichar_overflow = multichar_overflow or overflowed != 0;
8316 val += @as(u8, @truncate(item));
8317 }
8318 } else if (chars.items.len > 0) {
8319 val = chars.items[chars.items.len - 1];
8320 }
8321
8322 if (multichar_overflow) {
8323 char_literal_parser.err(.char_lit_too_wide, .{ .none = {} });
8324 }
8325
8326 for (char_literal_parser.errors()) |item| {
8327 try p.errExtra(item.tag, p.tok_i, item.extra);
8328 }
8329 }
8330
8331 const ty = char_kind.charLiteralType(p.comp);
8332 // This is the type the literal will have if we're in a macro; macros always operate on intmax_t/uintmax_t values
8333 const macro_ty = if (ty.isUnsignedInt(p.comp) or (char_kind == .char and p.comp.getCharSignedness() == .unsigned))
8334 p.comp.types.intmax.makeIntegerUnsigned()
8335 else
8336 p.comp.types.intmax;
8337
8338 var value = try Value.int(val, p.comp);
8339 // C99 6.4.4.4.10
8340 // > If an integer character constant contains a single character or escape sequence,
8341 // > its value is the one that results when an object with type char whose value is
8342 // > that of the single character or escape sequence is converted to type int.
8343 // This conversion only matters if `char` is signed and has a high-order bit of `1`
8344 if (char_kind == .char and !is_multichar and val > 0x7F and p.comp.getCharSignedness() == .signed) {
8345 _ = try value.intCast(.{ .specifier = .char }, p.comp);
8346 }
8347
8348 const res = Result{
8349 .ty = if (p.in_macro) macro_ty else ty,
8350 .val = value,
8351 .node = try p.addNode(.{ .tag = .char_literal, .ty = ty, .data = undefined, .loc = @enumFromInt(p.tok_i) }),
8352 };
8353 if (!p.in_macro) try p.value_map.put(res.node, res.val);
8354 return res;
8355}
8356
8357fn parseFloat(p: *Parser, buf: []const u8, suffix: NumberSuffix, tok_i: TokenIndex) !Result {
8358 const ty = Type{ .specifier = switch (suffix) {
8359 .None, .I => .double,
8360 .F, .IF => .float,
8361 .F16, .IF16 => .float16,
8362 .L, .IL => .long_double,
8363 .W, .IW => p.comp.float80Type().?.specifier,
8364 .Q, .IQ, .F128, .IF128 => .float128,
8365 else => unreachable,
8366 } };
8367 const val = try Value.intern(p.comp, key: {
8368 try p.strings.ensureUnusedCapacity(buf.len);
8369
8370 const strings_top = p.strings.items.len;
8371 defer p.strings.items.len = strings_top;
8372 for (buf) |c| {
8373 if (c != '\'') p.strings.appendAssumeCapacity(c);
8374 }
8375
8376 const float = std.fmt.parseFloat(f128, p.strings.items[strings_top..]) catch unreachable;
8377 const bits = ty.bitSizeof(p.comp).?;
8378 break :key switch (bits) {
8379 16 => .{ .float = .{ .f16 = @floatCast(float) } },
8380 32 => .{ .float = .{ .f32 = @floatCast(float) } },
8381 64 => .{ .float = .{ .f64 = @floatCast(float) } },
8382 80 => .{ .float = .{ .f80 = @floatCast(float) } },
8383 128 => .{ .float = .{ .f128 = @floatCast(float) } },
8384 else => unreachable,
8385 };
8386 });
8387 var res = Result{
8388 .ty = ty,
8389 .node = try p.addNode(.{ .tag = .float_literal, .ty = ty, .data = undefined, .loc = @enumFromInt(tok_i) }),
8390 .val = val,
8391 };
8392 if (suffix.isImaginary()) {
8393 try p.err(.gnu_imaginary_constant);
8394 res.ty = .{ .specifier = switch (suffix) {
8395 .I => .complex_double,
8396 .IF16 => .complex_float16,
8397 .IF => .complex_float,
8398 .IL => .complex_long_double,
8399 .IW => p.comp.float80Type().?.makeComplex().specifier,
8400 .IQ, .IF128 => .complex_float128,
8401 else => unreachable,
8402 } };
8403 res.val = try Value.intern(p.comp, switch (res.ty.bitSizeof(p.comp).?) {
8404 32 => .{ .complex = .{ .cf16 = .{ 0.0, val.toFloat(f16, p.comp) } } },
8405 64 => .{ .complex = .{ .cf32 = .{ 0.0, val.toFloat(f32, p.comp) } } },
8406 128 => .{ .complex = .{ .cf64 = .{ 0.0, val.toFloat(f64, p.comp) } } },
8407 160 => .{ .complex = .{ .cf80 = .{ 0.0, val.toFloat(f80, p.comp) } } },
8408 256 => .{ .complex = .{ .cf128 = .{ 0.0, val.toFloat(f128, p.comp) } } },
8409 else => unreachable,
8410 });
8411 try res.un(p, .imaginary_literal, tok_i);
8412 }
8413 return res;
8414}
8415
8416fn getIntegerPart(p: *Parser, buf: []const u8, prefix: NumberPrefix, tok_i: TokenIndex) ![]const u8 {
8417 if (buf[0] == '.') return "";
8418
8419 if (!prefix.digitAllowed(buf[0])) {
8420 switch (prefix) {
8421 .binary => try p.errExtra(.invalid_binary_digit, tok_i, .{ .ascii = @intCast(buf[0]) }),
8422 .octal => try p.errExtra(.invalid_octal_digit, tok_i, .{ .ascii = @intCast(buf[0]) }),
8423 .hex => try p.errStr(.invalid_int_suffix, tok_i, buf),
8424 .decimal => unreachable,
8425 }
8426 return error.ParsingFailed;
8427 }
8428
8429 for (buf, 0..) |c, idx| {
8430 if (idx == 0) continue;
8431 switch (c) {
8432 '.' => return buf[0..idx],
8433 'p', 'P' => return if (prefix == .hex) buf[0..idx] else {
8434 try p.errStr(.invalid_int_suffix, tok_i, buf[idx..]);
8435 return error.ParsingFailed;
8436 },
8437 'e', 'E' => {
8438 switch (prefix) {
8439 .hex => continue,
8440 .decimal => return buf[0..idx],
8441 .binary => try p.errExtra(.invalid_binary_digit, tok_i, .{ .ascii = @intCast(c) }),
8442 .octal => try p.errExtra(.invalid_octal_digit, tok_i, .{ .ascii = @intCast(c) }),
8443 }
8444 return error.ParsingFailed;
8445 },
8446 '0'...'9', 'a'...'d', 'A'...'D', 'f', 'F' => {
8447 if (!prefix.digitAllowed(c)) {
8448 switch (prefix) {
8449 .binary => try p.errExtra(.invalid_binary_digit, tok_i, .{ .ascii = @intCast(c) }),
8450 .octal => try p.errExtra(.invalid_octal_digit, tok_i, .{ .ascii = @intCast(c) }),
8451 .decimal, .hex => try p.errStr(.invalid_int_suffix, tok_i, buf[idx..]),
8452 }
8453 return error.ParsingFailed;
8454 }
8455 },
8456 '\'' => {},
8457 else => return buf[0..idx],
8458 }
8459 }
8460 return buf;
8461}
8462
8463fn fixedSizeInt(p: *Parser, base: u8, buf: []const u8, suffix: NumberSuffix, tok_i: TokenIndex) !Result {
8464 var val: u64 = 0;
8465 var overflow = false;
8466 for (buf) |c| {
8467 const digit: u64 = switch (c) {
8468 '0'...'9' => c - '0',
8469 'A'...'Z' => c - 'A' + 10,
8470 'a'...'z' => c - 'a' + 10,
8471 '\'' => continue,
8472 else => unreachable,
8473 };
8474
8475 if (val != 0) {
8476 const product, const overflowed = @mulWithOverflow(val, base);
8477 if (overflowed != 0) {
8478 overflow = true;
8479 }
8480 val = product;
8481 }
8482 const sum, const overflowed = @addWithOverflow(val, digit);
8483 if (overflowed != 0) overflow = true;
8484 val = sum;
8485 }
8486 var res: Result = .{ .val = try Value.int(val, p.comp) };
8487 if (overflow) {
8488 try p.errTok(.int_literal_too_big, tok_i);
8489 res.ty = .{ .specifier = .ulong_long };
8490 res.node = try p.addNode(.{ .tag = .int_literal, .ty = res.ty, .data = undefined, .loc = @enumFromInt(tok_i) });
8491 if (!p.in_macro) try p.value_map.put(res.node, res.val);
8492 return res;
8493 }
8494 const interned_val = try Value.int(val, p.comp);
8495 if (suffix.isSignedInteger()) {
8496 const max_int = try Value.maxInt(p.comp.types.intmax, p.comp);
8497 if (interned_val.compare(.gt, max_int, p.comp)) {
8498 try p.errTok(.implicitly_unsigned_literal, tok_i);
8499 }
8500 }
8501
8502 const signed_specs = .{ .int, .long, .long_long };
8503 const unsigned_specs = .{ .uint, .ulong, .ulong_long };
8504 const signed_oct_hex_specs = .{ .int, .uint, .long, .ulong, .long_long, .ulong_long };
8505 const specs: []const Type.Specifier = if (suffix.signedness() == .unsigned)
8506 &unsigned_specs
8507 else if (base == 10)
8508 &signed_specs
8509 else
8510 &signed_oct_hex_specs;
8511
8512 const suffix_ty: Type = .{ .specifier = switch (suffix) {
8513 .None, .I => .int,
8514 .U, .IU => .uint,
8515 .UL, .IUL => .ulong,
8516 .ULL, .IULL => .ulong_long,
8517 .L, .IL => .long,
8518 .LL, .ILL => .long_long,
8519 else => unreachable,
8520 } };
8521
8522 for (specs) |spec| {
8523 res.ty = Type{ .specifier = spec };
8524 if (res.ty.compareIntegerRanks(suffix_ty, p.comp).compare(.lt)) continue;
8525 const max_int = try Value.maxInt(res.ty, p.comp);
8526 if (interned_val.compare(.lte, max_int, p.comp)) break;
8527 } else {
8528 res.ty = .{ .specifier = spec: {
8529 if (p.comp.langopts.emulate == .gcc) {
8530 if (target_util.hasInt128(p.comp.target)) {
8531 break :spec .int128;
8532 } else {
8533 break :spec .long_long;
8534 }
8535 } else {
8536 break :spec .ulong_long;
8537 }
8538 } };
8539 }
8540
8541 res.node = try p.addNode(.{ .tag = .int_literal, .ty = res.ty, .data = undefined, .loc = @enumFromInt(tok_i) });
8542 if (!p.in_macro) try p.value_map.put(res.node, res.val);
8543 return res;
8544}
8545
8546fn parseInt(p: *Parser, prefix: NumberPrefix, buf: []const u8, suffix: NumberSuffix, tok_i: TokenIndex) !Result {
8547 if (prefix == .binary) {
8548 try p.errTok(.binary_integer_literal, tok_i);
8549 }
8550 const base = @intFromEnum(prefix);
8551 var res = if (suffix.isBitInt())
8552 try p.bitInt(base, buf, suffix, tok_i)
8553 else
8554 try p.fixedSizeInt(base, buf, suffix, tok_i);
8555
8556 if (suffix.isImaginary()) {
8557 try p.errTok(.gnu_imaginary_constant, tok_i);
8558 res.ty = res.ty.makeComplex();
8559 res.val = .{};
8560 try res.un(p, .imaginary_literal, tok_i);
8561 }
8562 return res;
8563}
8564
8565fn bitInt(p: *Parser, base: u8, buf: []const u8, suffix: NumberSuffix, tok_i: TokenIndex) Error!Result {
8566 try p.errStr(.pre_c23_compat, tok_i, "'_BitInt' suffix for literals");
8567 try p.errTok(.bitint_suffix, tok_i);
8568
8569 var managed = try big.int.Managed.init(p.gpa);
8570 defer managed.deinit();
8571
8572 {
8573 try p.strings.ensureUnusedCapacity(buf.len);
8574
8575 const strings_top = p.strings.items.len;
8576 defer p.strings.items.len = strings_top;
8577 for (buf) |c| {
8578 if (c != '\'') p.strings.appendAssumeCapacity(c);
8579 }
8580
8581 managed.setString(base, p.strings.items[strings_top..]) catch |e| switch (e) {
8582 error.InvalidBase => unreachable, // `base` is one of 2, 8, 10, 16
8583 error.InvalidCharacter => unreachable, // digits validated by Tokenizer
8584 else => |er| return er,
8585 };
8586 }
8587 const c = managed.toConst();
8588 const bits_needed: std.math.IntFittingRange(0, Compilation.bit_int_max_bits) = blk: {
8589 // Literal `0` requires at least 1 bit
8590 const count = @max(1, c.bitCountTwosComp());
8591 // The wb suffix results in a _BitInt that includes space for the sign bit even if the
8592 // value of the constant is positive or was specified in hexadecimal or octal notation.
8593 const sign_bits = @intFromBool(suffix.isSignedInteger());
8594 const bits_needed = count + sign_bits;
8595 break :blk @intCast(bits_needed);
8596 };
8597
8598 var res: Result = .{
8599 .val = try Value.intern(p.comp, .{ .int = .{ .big_int = c } }),
8600 .ty = .{
8601 .specifier = .bit_int,
8602 .data = .{ .int = .{ .bits = bits_needed, .signedness = suffix.signedness() } },
8603 },
8604 };
8605 res.node = try p.addNode(.{ .tag = .int_literal, .ty = res.ty, .data = undefined, .loc = @enumFromInt(tok_i) });
8606 if (!p.in_macro) try p.value_map.put(res.node, res.val);
8607 return res;
8608}
8609
8610fn getFracPart(p: *Parser, buf: []const u8, prefix: NumberPrefix, tok_i: TokenIndex) ![]const u8 {
8611 if (buf.len == 0 or buf[0] != '.') return "";
8612 assert(prefix != .octal);
8613 if (prefix == .binary) {
8614 try p.errStr(.invalid_int_suffix, tok_i, buf);
8615 return error.ParsingFailed;
8616 }
8617 for (buf, 0..) |c, idx| {
8618 if (idx == 0) continue;
8619 if (c == '\'') continue;
8620 if (!prefix.digitAllowed(c)) return buf[0..idx];
8621 }
8622 return buf;
8623}
8624
8625fn getExponent(p: *Parser, buf: []const u8, prefix: NumberPrefix, tok_i: TokenIndex) ![]const u8 {
8626 if (buf.len == 0) return "";
8627
8628 switch (buf[0]) {
8629 'e', 'E' => assert(prefix == .decimal),
8630 'p', 'P' => if (prefix != .hex) {
8631 try p.errStr(.invalid_float_suffix, tok_i, buf);
8632 return error.ParsingFailed;
8633 },
8634 else => return "",
8635 }
8636 const end = for (buf, 0..) |c, idx| {
8637 if (idx == 0) continue;
8638 if (idx == 1 and (c == '+' or c == '-')) continue;
8639 switch (c) {
8640 '0'...'9' => {},
8641 '\'' => continue,
8642 else => break idx,
8643 }
8644 } else buf.len;
8645 const exponent = buf[0..end];
8646 if (std.mem.indexOfAny(u8, exponent, "0123456789") == null) {
8647 try p.errTok(.exponent_has_no_digits, tok_i);
8648 return error.ParsingFailed;
8649 }
8650 return exponent;
8651}
8652
8653/// Using an explicit `tok_i` parameter instead of `p.tok_i` makes it easier
8654/// to parse numbers in pragma handlers.
8655pub fn parseNumberToken(p: *Parser, tok_i: TokenIndex) !Result {
8656 const buf = p.tokSlice(tok_i);
8657 const prefix = NumberPrefix.fromString(buf);
8658 const after_prefix = buf[prefix.stringLen()..];
8659
8660 const int_part = try p.getIntegerPart(after_prefix, prefix, tok_i);
8661
8662 const after_int = after_prefix[int_part.len..];
8663
8664 const frac = try p.getFracPart(after_int, prefix, tok_i);
8665 const after_frac = after_int[frac.len..];
8666
8667 const exponent = try p.getExponent(after_frac, prefix, tok_i);
8668 const suffix_str = after_frac[exponent.len..];
8669 const is_float = (exponent.len > 0 or frac.len > 0);
8670 const suffix = NumberSuffix.fromString(suffix_str, if (is_float) .float else .int) orelse {
8671 if (is_float) {
8672 try p.errStr(.invalid_float_suffix, tok_i, suffix_str);
8673 } else {
8674 try p.errStr(.invalid_int_suffix, tok_i, suffix_str);
8675 }
8676 return error.ParsingFailed;
8677 };
8678 if (suffix.isFloat80() and p.comp.float80Type() == null) {
8679 try p.errStr(.invalid_float_suffix, tok_i, suffix_str);
8680 return error.ParsingFailed;
8681 }
8682
8683 if (is_float) {
8684 assert(prefix == .hex or prefix == .decimal);
8685 if (prefix == .hex and exponent.len == 0) {
8686 try p.errTok(.hex_floating_constant_requires_exponent, tok_i);
8687 return error.ParsingFailed;
8688 }
8689 const number = buf[0 .. buf.len - suffix_str.len];
8690 return p.parseFloat(number, suffix, tok_i);
8691 } else {
8692 return p.parseInt(prefix, int_part, suffix, tok_i);
8693 }
8694}
8695
8696fn ppNum(p: *Parser) Error!Result {
8697 defer p.tok_i += 1;
8698 var res = try p.parseNumberToken(p.tok_i);
8699 if (p.in_macro) {
8700 if (res.ty.isFloat() or !res.ty.isReal()) {
8701 try p.errTok(.float_literal_in_pp_expr, p.tok_i);
8702 return error.ParsingFailed;
8703 }
8704 res.ty = if (res.ty.isUnsignedInt(p.comp)) p.comp.types.intmax.makeIntegerUnsigned() else p.comp.types.intmax;
8705 } else if (res.val.opt_ref != .none) {
8706 try p.value_map.put(res.node, res.val);
8707 }
8708 return res;
8709}
8710
8711/// Run a parser function but do not evaluate the result
8712fn parseNoEval(p: *Parser, comptime func: fn (*Parser) Error!Result) Error!Result {
8713 const no_eval = p.no_eval;
8714 defer p.no_eval = no_eval;
8715 p.no_eval = true;
8716 const parsed = try func(p);
8717 try parsed.expect(p);
8718 return parsed;
8719}
8720
8721/// genericSelection : keyword_generic '(' assignExpr ',' genericAssoc (',' genericAssoc)* ')'
8722/// genericAssoc
8723/// : typeName ':' assignExpr
8724/// | keyword_default ':' assignExpr
8725fn genericSelection(p: *Parser) Error!Result {
8726 const kw_generic = p.tok_i;
8727 p.tok_i += 1;
8728 const l_paren = try p.expectToken(.l_paren);
8729 const controlling_tok = p.tok_i;
8730 const controlling = try p.parseNoEval(assignExpr);
8731 _ = try p.expectToken(.comma);
8732 var controlling_ty = controlling.ty;
8733 if (controlling_ty.isArray()) controlling_ty.decayArray();
8734
8735 const list_buf_top = p.list_buf.items.len;
8736 defer p.list_buf.items.len = list_buf_top;
8737 try p.list_buf.append(controlling.node);
8738
8739 // Use decl_buf to store the token indexes of previous cases
8740 const decl_buf_top = p.decl_buf.items.len;
8741 defer p.decl_buf.items.len = decl_buf_top;
8742
8743 var default_tok: ?TokenIndex = null;
8744 var default: Result = undefined;
8745 var chosen_tok: TokenIndex = undefined;
8746 var chosen: Result = .{};
8747 while (true) {
8748 const start = p.tok_i;
8749 if (try p.typeName()) |ty| blk: {
8750 if (ty.isArray()) {
8751 try p.errTok(.generic_array_type, start);
8752 } else if (ty.isFunc()) {
8753 try p.errTok(.generic_func_type, start);
8754 } else if (ty.anyQual()) {
8755 try p.errTok(.generic_qual_type, start);
8756 }
8757 _ = try p.expectToken(.colon);
8758 const node = try p.assignExpr();
8759 try node.expect(p);
8760
8761 if (ty.eql(controlling_ty, p.comp, false)) {
8762 if (chosen.node == .none) {
8763 chosen = node;
8764 chosen_tok = start;
8765 break :blk;
8766 }
8767 try p.errStr(.generic_duplicate, start, try p.typeStr(ty));
8768 try p.errStr(.generic_duplicate_here, chosen_tok, try p.typeStr(ty));
8769 }
8770 const list_buf = p.list_buf.items[list_buf_top + 1 ..];
8771 const decl_buf = p.decl_buf.items[decl_buf_top..];
8772 if (list_buf.len == decl_buf.len) {
8773 // If these do not have the same length, there is already an error
8774 for (list_buf, decl_buf) |item, prev_tok| {
8775 const prev_ty = p.nodes.items(.ty)[@intFromEnum(item)];
8776 if (prev_ty.eql(ty, p.comp, true)) {
8777 try p.errStr(.generic_duplicate, start, try p.typeStr(ty));
8778 try p.errStr(.generic_duplicate_here, @intFromEnum(prev_tok), try p.typeStr(ty));
8779 }
8780 }
8781 }
8782 try p.list_buf.append(try p.addNode(.{
8783 .tag = .generic_association_expr,
8784 .ty = ty,
8785 .data = .{ .un = node.node },
8786 .loc = @enumFromInt(start),
8787 }));
8788 try p.decl_buf.append(@enumFromInt(start));
8789 } else if (p.eatToken(.keyword_default)) |tok| {
8790 if (default_tok) |prev| {
8791 try p.errTok(.generic_duplicate_default, tok);
8792 try p.errTok(.previous_case, prev);
8793 }
8794 default_tok = tok;
8795 _ = try p.expectToken(.colon);
8796 default = try p.assignExpr();
8797 try default.expect(p);
8798 } else {
8799 if (p.list_buf.items.len == list_buf_top + 1) {
8800 try p.err(.expected_type);
8801 return error.ParsingFailed;
8802 }
8803 break;
8804 }
8805 if (p.eatToken(.comma) == null) break;
8806 }
8807 try p.expectClosing(l_paren, .r_paren);
8808
8809 if (chosen.node == .none) {
8810 if (default_tok) |tok| {
8811 try p.list_buf.insert(list_buf_top + 1, try p.addNode(.{
8812 .tag = .generic_default_expr,
8813 .data = .{ .un = default.node },
8814 .ty = default.ty,
8815 .loc = @enumFromInt(tok),
8816 }));
8817 chosen = default;
8818 } else {
8819 try p.errStr(.generic_no_match, controlling_tok, try p.typeStr(controlling_ty));
8820 return error.ParsingFailed;
8821 }
8822 } else {
8823 try p.list_buf.insert(list_buf_top + 1, try p.addNode(.{
8824 .tag = .generic_association_expr,
8825 .data = .{ .un = chosen.node },
8826 .ty = chosen.ty,
8827 .loc = @enumFromInt(chosen_tok),
8828 }));
8829 if (default_tok) |tok| {
8830 try p.list_buf.append(try p.addNode(.{
8831 .tag = .generic_default_expr,
8832 .data = .{ .un = default.node },
8833 .ty = default.ty,
8834 .loc = @enumFromInt(tok),
8835 }));
8836 }
8837 }
8838
8839 var generic_node: Tree.Node = .{
8840 .tag = .generic_expr_one,
8841 .ty = chosen.ty,
8842 .data = .{ .two = .{ controlling.node, chosen.node } },
8843 .loc = @enumFromInt(kw_generic),
8844 };
8845 const associations = p.list_buf.items[list_buf_top..];
8846 if (associations.len > 2) { // associations[0] == controlling.node
8847 generic_node.tag = .generic_expr;
8848 generic_node.data = .{ .range = try p.addList(associations) };
8849 }
8850 chosen.node = try p.addNode(generic_node);
8851 return chosen;
8852}
8853
8854test "Node locations" {
8855 var comp = Compilation.init(std.testing.allocator, std.fs.cwd());
8856 defer comp.deinit();
8857
8858 const file = try comp.addSourceFromBuffer("file.c",
8859 \\int foo = 5;
8860 \\int bar = 10;
8861 \\int main(void) {}
8862 \\
8863 );
8864
8865 const builtin_macros = try comp.generateBuiltinMacros(.no_system_defines);
8866
8867 var pp = Preprocessor.init(&comp);
8868 defer pp.deinit();
8869 try pp.addBuiltinMacros();
8870
8871 _ = try pp.preprocess(builtin_macros);
8872
8873 const eof = try pp.preprocess(file);
8874 try pp.addToken(eof);
8875
8876 var tree = try Parser.parse(&pp);
8877 defer tree.deinit();
8878
8879 try std.testing.expectEqual(0, comp.diagnostics.list.items.len);
8880 for (tree.root_decls, 0..) |node, i| {
8881 const tok_i = tree.nodeTok(node).?;
8882 const slice = tree.tokSlice(tok_i);
8883 const expected = switch (i) {
8884 0 => "foo",
8885 1 => "bar",
8886 2 => "main",
8887 else => unreachable,
8888 };
8889 try std.testing.expectEqualStrings(expected, slice);
8890 }
8891}
lib/compiler/aro/aro/Pragma.zig deleted-83
...@@ -1,83 +0,0 @@
1const std = @import("std");
2const Compilation = @import("Compilation.zig");
3const Preprocessor = @import("Preprocessor.zig");
4const Parser = @import("Parser.zig");
5const TokenIndex = @import("Tree.zig").TokenIndex;
6
7pub const Error = Compilation.Error || error{ UnknownPragma, StopPreprocessing };
8
9const Pragma = @This();
10
11/// Called during Preprocessor.init
12beforePreprocess: ?*const fn (*Pragma, *Compilation) void = null,
13
14/// Called at the beginning of Parser.parse
15beforeParse: ?*const fn (*Pragma, *Compilation) void = null,
16
17/// Called at the end of Parser.parse if a Tree was successfully parsed
18afterParse: ?*const fn (*Pragma, *Compilation) void = null,
19
20/// Called during Compilation.deinit
21deinit: *const fn (*Pragma, *Compilation) void,
22
23/// Called whenever the preprocessor encounters this pragma. `start_idx` is the index
24/// within `pp.tokens` of the pragma name token. The pragma end is indicated by a
25/// .nl token (which may be generated if the source ends with a pragma with no newline)
26/// As an example, given the following line:
27/// #pragma GCC diagnostic error "-Wnewline-eof" \n
28/// Then pp.tokens.get(start_idx) will return the `GCC` token.
29/// Return error.UnknownPragma to emit an `unknown_pragma` diagnostic
30/// Return error.StopPreprocessing to stop preprocessing the current file (see once.zig)
31preprocessorHandler: ?*const fn (*Pragma, *Preprocessor, start_idx: TokenIndex) Error!void = null,
32
33/// Called during token pretty-printing (`-E` option). If this returns true, the pragma will
34/// be printed; otherwise it will be omitted. start_idx is the index of the pragma name token
35preserveTokens: ?*const fn (*Pragma, *Preprocessor, start_idx: TokenIndex) bool = null,
36
37/// Same as preprocessorHandler except called during parsing
38/// The parser's `p.tok_i` field must not be changed
39parserHandler: ?*const fn (*Pragma, *Parser, start_idx: TokenIndex) Compilation.Error!void = null,
40
41pub fn pasteTokens(pp: *Preprocessor, start_idx: TokenIndex) ![]const u8 {
42 if (pp.tokens.get(start_idx).id == .nl) return error.ExpectedStringLiteral;
43
44 const char_top = pp.char_buf.items.len;
45 defer pp.char_buf.items.len = char_top;
46 var i: usize = 0;
47 var lparen_count: u32 = 0;
48 var rparen_count: u32 = 0;
49 while (true) : (i += 1) {
50 const tok = pp.tokens.get(start_idx + i);
51 if (tok.id == .nl) break;
52 switch (tok.id) {
53 .l_paren => {
54 if (lparen_count != i) return error.ExpectedStringLiteral;
55 lparen_count += 1;
56 },
57 .r_paren => rparen_count += 1,
58 .string_literal => {
59 if (rparen_count != 0) return error.ExpectedStringLiteral;
60 const str = pp.expandedSlice(tok);
61 try pp.char_buf.appendSlice(str[1 .. str.len - 1]);
62 },
63 else => return error.ExpectedStringLiteral,
64 }
65 }
66 if (lparen_count != rparen_count) return error.ExpectedStringLiteral;
67 return pp.char_buf.items[char_top..];
68}
69
70pub fn shouldPreserveTokens(self: *Pragma, pp: *Preprocessor, start_idx: TokenIndex) bool {
71 if (self.preserveTokens) |func| return func(self, pp, start_idx);
72 return false;
73}
74
75pub fn preprocessorCB(self: *Pragma, pp: *Preprocessor, start_idx: TokenIndex) Error!void {
76 if (self.preprocessorHandler) |func| return func(self, pp, start_idx);
77}
78
79pub fn parserCB(self: *Pragma, p: *Parser, start_idx: TokenIndex) Compilation.Error!void {
80 const tok_index = p.tok_i;
81 defer std.debug.assert(tok_index == p.tok_i);
82 if (self.parserHandler) |func| return func(self, p, start_idx);
83}
lib/compiler/aro/aro/Preprocessor.zig deleted-3649
...@@ -1,3649 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const Allocator = mem.Allocator;
4const assert = std.debug.assert;
5const Compilation = @import("Compilation.zig");
6const Error = Compilation.Error;
7const Source = @import("Source.zig");
8const Tokenizer = @import("Tokenizer.zig");
9const RawToken = Tokenizer.Token;
10const Parser = @import("Parser.zig");
11const Diagnostics = @import("Diagnostics.zig");
12const Tree = @import("Tree.zig");
13const Token = Tree.Token;
14const TokenWithExpansionLocs = Tree.TokenWithExpansionLocs;
15const Attribute = @import("Attribute.zig");
16const features = @import("features.zig");
17const Hideset = @import("Hideset.zig");
18
19const DefineMap = std.StringHashMapUnmanaged(Macro);
20const RawTokenList = std.ArrayList(RawToken);
21const max_include_depth = 200;
22
23/// Errors that can be returned when expanding a macro.
24/// error.UnknownPragma can occur within Preprocessor.pragma() but
25/// it is handled there and doesn't escape that function
26const MacroError = Error || error{StopPreprocessing};
27
28const Macro = struct {
29 /// Parameters of the function type macro
30 params: []const []const u8,
31
32 /// Token constituting the macro body
33 tokens: []const RawToken,
34
35 /// If the function type macro has variable number of arguments
36 var_args: bool,
37
38 /// Is a function type macro
39 is_func: bool,
40
41 /// Is a predefined macro
42 is_builtin: bool = false,
43
44 /// Location of macro in the source
45 loc: Source.Location,
46
47 fn eql(a: Macro, b: Macro, pp: *Preprocessor) bool {
48 if (a.tokens.len != b.tokens.len) return false;
49 if (a.is_builtin != b.is_builtin) return false;
50 for (a.tokens, b.tokens) |a_tok, b_tok| if (!tokEql(pp, a_tok, b_tok)) return false;
51
52 if (a.is_func and b.is_func) {
53 if (a.var_args != b.var_args) return false;
54 if (a.params.len != b.params.len) return false;
55 for (a.params, b.params) |a_param, b_param| if (!mem.eql(u8, a_param, b_param)) return false;
56 }
57
58 return true;
59 }
60
61 fn tokEql(pp: *Preprocessor, a: RawToken, b: RawToken) bool {
62 return mem.eql(u8, pp.tokSlice(a), pp.tokSlice(b));
63 }
64};
65
66const Preprocessor = @This();
67
68const ExpansionEntry = struct {
69 idx: Tree.TokenIndex,
70 locs: [*]Source.Location,
71};
72
73const TokenState = struct {
74 tokens_len: usize,
75 expansion_entries_len: usize,
76};
77
78comp: *Compilation,
79gpa: mem.Allocator,
80arena: std.heap.ArenaAllocator,
81defines: DefineMap = .{},
82/// Do not directly mutate this; use addToken / addTokenAssumeCapacity / ensureTotalTokenCapacity / ensureUnusedTokenCapacity
83tokens: Token.List = .{},
84/// Do not directly mutate this; must be kept in sync with `tokens`
85expansion_entries: std.MultiArrayList(ExpansionEntry) = .{},
86token_buf: RawTokenList,
87char_buf: std.ArrayList(u8),
88/// Counter that is incremented each time preprocess() is called
89/// Can be used to distinguish multiple preprocessings of the same file
90preprocess_count: u32 = 0,
91generated_line: u32 = 1,
92add_expansion_nl: u32 = 0,
93include_depth: u8 = 0,
94counter: u32 = 0,
95expansion_source_loc: Source.Location = undefined,
96poisoned_identifiers: std.StringHashMap(void),
97/// Map from Source.Id to macro name in the `#ifndef` condition which guards the source, if any
98include_guards: std.AutoHashMapUnmanaged(Source.Id, []const u8) = .empty,
99
100/// Store `keyword_define` and `keyword_undef` tokens.
101/// Used to implement preprocessor debug dump options
102/// Must be false unless in -E mode (parser does not handle those token types)
103store_macro_tokens: bool = false,
104
105/// Memory is retained to avoid allocation on every single token.
106top_expansion_buf: ExpandBuf,
107
108/// Dump current state to stderr.
109verbose: bool = false,
110preserve_whitespace: bool = false,
111
112/// linemarker tokens. Must be .none unless in -E mode (parser does not handle linemarkers)
113linemarkers: Linemarkers = .none,
114
115hideset: Hideset,
116
117pub const parse = Parser.parse;
118
119pub const Linemarkers = enum {
120 /// No linemarker tokens. Required setting if parser will run
121 none,
122 /// #line <num> "filename"
123 line_directives,
124 /// # <num> "filename" flags
125 numeric_directives,
126};
127
128pub fn init(comp: *Compilation) Preprocessor {
129 const pp = Preprocessor{
130 .comp = comp,
131 .gpa = comp.gpa,
132 .arena = std.heap.ArenaAllocator.init(comp.gpa),
133 .token_buf = RawTokenList.init(comp.gpa),
134 .char_buf = std.ArrayList(u8).init(comp.gpa),
135 .poisoned_identifiers = std.StringHashMap(void).init(comp.gpa),
136 .top_expansion_buf = ExpandBuf.init(comp.gpa),
137 .hideset = .{ .comp = comp },
138 };
139 comp.pragmaEvent(.before_preprocess);
140 return pp;
141}
142
143/// Initialize Preprocessor with builtin macros.
144pub fn initDefault(comp: *Compilation) !Preprocessor {
145 var pp = init(comp);
146 errdefer pp.deinit();
147 try pp.addBuiltinMacros();
148 return pp;
149}
150
151const builtin_macros = struct {
152 const args = [1][]const u8{"X"};
153
154 const has_attribute = [1]RawToken{.{
155 .id = .macro_param_has_attribute,
156 .source = .generated,
157 }};
158 const has_c_attribute = [1]RawToken{.{
159 .id = .macro_param_has_c_attribute,
160 .source = .generated,
161 }};
162 const has_declspec_attribute = [1]RawToken{.{
163 .id = .macro_param_has_declspec_attribute,
164 .source = .generated,
165 }};
166 const has_warning = [1]RawToken{.{
167 .id = .macro_param_has_warning,
168 .source = .generated,
169 }};
170 const has_feature = [1]RawToken{.{
171 .id = .macro_param_has_feature,
172 .source = .generated,
173 }};
174 const has_extension = [1]RawToken{.{
175 .id = .macro_param_has_extension,
176 .source = .generated,
177 }};
178 const has_builtin = [1]RawToken{.{
179 .id = .macro_param_has_builtin,
180 .source = .generated,
181 }};
182 const has_include = [1]RawToken{.{
183 .id = .macro_param_has_include,
184 .source = .generated,
185 }};
186 const has_include_next = [1]RawToken{.{
187 .id = .macro_param_has_include_next,
188 .source = .generated,
189 }};
190 const has_embed = [1]RawToken{.{
191 .id = .macro_param_has_embed,
192 .source = .generated,
193 }};
194
195 const is_identifier = [1]RawToken{.{
196 .id = .macro_param_is_identifier,
197 .source = .generated,
198 }};
199
200 const pragma_operator = [1]RawToken{.{
201 .id = .macro_param_pragma_operator,
202 .source = .generated,
203 }};
204
205 const file = [1]RawToken{.{
206 .id = .macro_file,
207 .source = .generated,
208 }};
209 const line = [1]RawToken{.{
210 .id = .macro_line,
211 .source = .generated,
212 }};
213 const counter = [1]RawToken{.{
214 .id = .macro_counter,
215 .source = .generated,
216 }};
217};
218
219fn addBuiltinMacro(pp: *Preprocessor, name: []const u8, is_func: bool, tokens: []const RawToken) !void {
220 try pp.defines.putNoClobber(pp.gpa, name, .{
221 .params = &builtin_macros.args,
222 .tokens = tokens,
223 .var_args = false,
224 .is_func = is_func,
225 .loc = .{ .id = .generated },
226 .is_builtin = true,
227 });
228}
229
230pub fn addBuiltinMacros(pp: *Preprocessor) !void {
231 try pp.addBuiltinMacro("__has_attribute", true, &builtin_macros.has_attribute);
232 try pp.addBuiltinMacro("__has_c_attribute", true, &builtin_macros.has_c_attribute);
233 try pp.addBuiltinMacro("__has_declspec_attribute", true, &builtin_macros.has_declspec_attribute);
234 try pp.addBuiltinMacro("__has_warning", true, &builtin_macros.has_warning);
235 try pp.addBuiltinMacro("__has_feature", true, &builtin_macros.has_feature);
236 try pp.addBuiltinMacro("__has_extension", true, &builtin_macros.has_extension);
237 try pp.addBuiltinMacro("__has_builtin", true, &builtin_macros.has_builtin);
238 try pp.addBuiltinMacro("__has_include", true, &builtin_macros.has_include);
239 try pp.addBuiltinMacro("__has_include_next", true, &builtin_macros.has_include_next);
240 try pp.addBuiltinMacro("__has_embed", true, &builtin_macros.has_embed);
241 try pp.addBuiltinMacro("__is_identifier", true, &builtin_macros.is_identifier);
242 try pp.addBuiltinMacro("_Pragma", true, &builtin_macros.pragma_operator);
243
244 try pp.addBuiltinMacro("__FILE__", false, &builtin_macros.file);
245 try pp.addBuiltinMacro("__LINE__", false, &builtin_macros.line);
246 try pp.addBuiltinMacro("__COUNTER__", false, &builtin_macros.counter);
247}
248
249pub fn deinit(pp: *Preprocessor) void {
250 pp.defines.deinit(pp.gpa);
251 pp.tokens.deinit(pp.gpa);
252 pp.arena.deinit();
253 pp.token_buf.deinit();
254 pp.char_buf.deinit();
255 pp.poisoned_identifiers.deinit();
256 pp.include_guards.deinit(pp.gpa);
257 pp.top_expansion_buf.deinit();
258 pp.hideset.deinit();
259 for (pp.expansion_entries.items(.locs)) |locs| TokenWithExpansionLocs.free(locs, pp.gpa);
260 pp.expansion_entries.deinit(pp.gpa);
261}
262
263/// Free buffers that are not needed after preprocessing
264fn clearBuffers(pp: *Preprocessor) void {
265 pp.token_buf.clearAndFree();
266 pp.char_buf.clearAndFree();
267 pp.top_expansion_buf.clearAndFree();
268 pp.hideset.clearAndFree();
269}
270
271pub fn expansionSlice(pp: *Preprocessor, tok: Tree.TokenIndex) []Source.Location {
272 const S = struct {
273 fn orderTokenIndex(context: Tree.TokenIndex, item: Tree.TokenIndex) std.math.Order {
274 return std.math.order(context, item);
275 }
276 };
277
278 const indices = pp.expansion_entries.items(.idx);
279 const idx = std.sort.binarySearch(Tree.TokenIndex, indices, tok, S.orderTokenIndex) orelse return &.{};
280 const locs = pp.expansion_entries.items(.locs)[idx];
281 var i: usize = 0;
282 while (locs[i].id != .unused) : (i += 1) {}
283 return locs[0..i];
284}
285
286/// Preprocess a compilation unit of sources into a parsable list of tokens.
287pub fn preprocessSources(pp: *Preprocessor, sources: []const Source) Error!void {
288 assert(sources.len > 1);
289 const first = sources[0];
290 try pp.addIncludeStart(first);
291 for (sources[1..]) |header| {
292 try pp.addIncludeStart(header);
293 _ = try pp.preprocess(header);
294 }
295 try pp.addIncludeResume(first.id, 0, 1);
296 const eof = try pp.preprocess(first);
297 try pp.addToken(eof);
298 pp.clearBuffers();
299}
300
301/// Preprocess a source file, returns eof token.
302pub fn preprocess(pp: *Preprocessor, source: Source) Error!TokenWithExpansionLocs {
303 const eof = pp.preprocessExtra(source) catch |er| switch (er) {
304 // This cannot occur in the main file and is handled in `include`.
305 error.StopPreprocessing => unreachable,
306 else => |e| return e,
307 };
308 try eof.checkMsEof(source, pp.comp);
309 return eof;
310}
311
312/// Tokenize a file without any preprocessing, returns eof token.
313pub fn tokenize(pp: *Preprocessor, source: Source) Error!Token {
314 assert(pp.linemarkers == .none);
315 assert(pp.preserve_whitespace == false);
316 var tokenizer = Tokenizer{
317 .buf = source.buf,
318 .comp = pp.comp,
319 .source = source.id,
320 };
321
322 // Estimate how many new tokens this source will contain.
323 const estimated_token_count = source.buf.len / 8;
324 try pp.ensureTotalTokenCapacity(pp.tokens.len + estimated_token_count);
325
326 while (true) {
327 const tok = tokenizer.next();
328 if (tok.id == .eof) return tokFromRaw(tok);
329 try pp.addToken(tokFromRaw(tok));
330 }
331}
332
333pub fn addIncludeStart(pp: *Preprocessor, source: Source) !void {
334 if (pp.linemarkers == .none) return;
335 try pp.addToken(.{ .id = .include_start, .loc = .{
336 .id = source.id,
337 .byte_offset = std.math.maxInt(u32),
338 .line = 1,
339 } });
340}
341
342pub fn addIncludeResume(pp: *Preprocessor, source: Source.Id, offset: u32, line: u32) !void {
343 if (pp.linemarkers == .none) return;
344 try pp.addToken(.{ .id = .include_resume, .loc = .{
345 .id = source,
346 .byte_offset = offset,
347 .line = line,
348 } });
349}
350
351fn invalidTokenDiagnostic(tok_id: Token.Id) Diagnostics.Tag {
352 return switch (tok_id) {
353 .unterminated_string_literal => .unterminated_string_literal_warning,
354 .empty_char_literal => .empty_char_literal_warning,
355 .unterminated_char_literal => .unterminated_char_literal_warning,
356 else => unreachable,
357 };
358}
359
360/// Return the name of the #ifndef guard macro that starts a source, if any.
361fn findIncludeGuard(pp: *Preprocessor, source: Source) ?[]const u8 {
362 var tokenizer = Tokenizer{
363 .buf = source.buf,
364 .langopts = pp.comp.langopts,
365 .source = source.id,
366 };
367 var hash = tokenizer.nextNoWS();
368 while (hash.id == .nl) hash = tokenizer.nextNoWS();
369 if (hash.id != .hash) return null;
370 const ifndef = tokenizer.nextNoWS();
371 if (ifndef.id != .keyword_ifndef) return null;
372 const guard = tokenizer.nextNoWS();
373 if (guard.id != .identifier) return null;
374 return pp.tokSlice(guard);
375}
376
377fn preprocessExtra(pp: *Preprocessor, source: Source) MacroError!TokenWithExpansionLocs {
378 var guard_name = pp.findIncludeGuard(source);
379
380 pp.preprocess_count += 1;
381 var tokenizer = Tokenizer{
382 .buf = source.buf,
383 .langopts = pp.comp.langopts,
384 .source = source.id,
385 };
386
387 // Estimate how many new tokens this source will contain.
388 const estimated_token_count = source.buf.len / 8;
389 try pp.ensureTotalTokenCapacity(pp.tokens.len + estimated_token_count);
390
391 var if_level: u8 = 0;
392 var if_kind: [64]u8 = .{0} ** 64;
393 const until_else = 0;
394 const until_endif = 1;
395 const until_endif_seen_else = 2;
396
397 var start_of_line = true;
398 while (true) {
399 var tok = tokenizer.next();
400 switch (tok.id) {
401 .hash => if (!start_of_line) try pp.addToken(tokFromRaw(tok)) else {
402 const directive = tokenizer.nextNoWS();
403 switch (directive.id) {
404 .keyword_error, .keyword_warning => {
405 // #error tokens..
406 pp.top_expansion_buf.items.len = 0;
407 const char_top = pp.char_buf.items.len;
408 defer pp.char_buf.items.len = char_top;
409
410 while (true) {
411 tok = tokenizer.next();
412 if (tok.id == .nl or tok.id == .eof) break;
413 if (tok.id == .whitespace) tok.id = .macro_ws;
414 try pp.top_expansion_buf.append(tokFromRaw(tok));
415 }
416 try pp.stringify(pp.top_expansion_buf.items);
417 const slice = pp.char_buf.items[char_top + 1 .. pp.char_buf.items.len - 2];
418 const duped = try pp.comp.diagnostics.arena.allocator().dupe(u8, slice);
419
420 try pp.comp.addDiagnostic(.{
421 .tag = if (directive.id == .keyword_error) .error_directive else .warning_directive,
422 .loc = .{ .id = tok.source, .byte_offset = directive.start, .line = directive.line },
423 .extra = .{ .str = duped },
424 }, &.{});
425 },
426 .keyword_if => {
427 const sum, const overflowed = @addWithOverflow(if_level, 1);
428 if (overflowed != 0)
429 return pp.fatal(directive, "too many #if nestings", .{});
430 if_level = sum;
431
432 if (try pp.expr(&tokenizer)) {
433 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
434 if (pp.verbose) {
435 pp.verboseLog(directive, "entering then branch of #if", .{});
436 }
437 } else {
438 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
439 try pp.skip(&tokenizer, .until_else);
440 if (pp.verbose) {
441 pp.verboseLog(directive, "entering else branch of #if", .{});
442 }
443 }
444 },
445 .keyword_ifdef => {
446 const sum, const overflowed = @addWithOverflow(if_level, 1);
447 if (overflowed != 0)
448 return pp.fatal(directive, "too many #if nestings", .{});
449 if_level = sum;
450
451 const macro_name = (try pp.expectMacroName(&tokenizer)) orelse continue;
452 try pp.expectNl(&tokenizer);
453 if (pp.defines.get(macro_name) != null) {
454 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
455 if (pp.verbose) {
456 pp.verboseLog(directive, "entering then branch of #ifdef", .{});
457 }
458 } else {
459 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
460 try pp.skip(&tokenizer, .until_else);
461 if (pp.verbose) {
462 pp.verboseLog(directive, "entering else branch of #ifdef", .{});
463 }
464 }
465 },
466 .keyword_ifndef => {
467 const sum, const overflowed = @addWithOverflow(if_level, 1);
468 if (overflowed != 0)
469 return pp.fatal(directive, "too many #if nestings", .{});
470 if_level = sum;
471
472 const macro_name = (try pp.expectMacroName(&tokenizer)) orelse continue;
473 try pp.expectNl(&tokenizer);
474 if (pp.defines.get(macro_name) == null) {
475 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
476 } else {
477 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
478 try pp.skip(&tokenizer, .until_else);
479 }
480 },
481 .keyword_elif => {
482 if (if_level == 0) {
483 try pp.err(directive, .elif_without_if);
484 if_level += 1;
485 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
486 } else if (if_level == 1) {
487 guard_name = null;
488 }
489 switch (std.mem.readPackedIntNative(u2, &if_kind, if_level * 2)) {
490 until_else => if (try pp.expr(&tokenizer)) {
491 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
492 if (pp.verbose) {
493 pp.verboseLog(directive, "entering then branch of #elif", .{});
494 }
495 } else {
496 try pp.skip(&tokenizer, .until_else);
497 if (pp.verbose) {
498 pp.verboseLog(directive, "entering else branch of #elif", .{});
499 }
500 },
501 until_endif => try pp.skip(&tokenizer, .until_endif),
502 until_endif_seen_else => {
503 try pp.err(directive, .elif_after_else);
504 skipToNl(&tokenizer);
505 },
506 else => unreachable,
507 }
508 },
509 .keyword_elifdef => {
510 if (if_level == 0) {
511 try pp.err(directive, .elifdef_without_if);
512 if_level += 1;
513 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
514 } else if (if_level == 1) {
515 guard_name = null;
516 }
517 switch (std.mem.readPackedIntNative(u2, &if_kind, if_level * 2)) {
518 until_else => {
519 const macro_name = try pp.expectMacroName(&tokenizer);
520 if (macro_name == null) {
521 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
522 try pp.skip(&tokenizer, .until_else);
523 if (pp.verbose) {
524 pp.verboseLog(directive, "entering else branch of #elifdef", .{});
525 }
526 } else {
527 try pp.expectNl(&tokenizer);
528 if (pp.defines.get(macro_name.?) != null) {
529 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
530 if (pp.verbose) {
531 pp.verboseLog(directive, "entering then branch of #elifdef", .{});
532 }
533 } else {
534 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
535 try pp.skip(&tokenizer, .until_else);
536 if (pp.verbose) {
537 pp.verboseLog(directive, "entering else branch of #elifdef", .{});
538 }
539 }
540 }
541 },
542 until_endif => try pp.skip(&tokenizer, .until_endif),
543 until_endif_seen_else => {
544 try pp.err(directive, .elifdef_after_else);
545 skipToNl(&tokenizer);
546 },
547 else => unreachable,
548 }
549 },
550 .keyword_elifndef => {
551 if (if_level == 0) {
552 try pp.err(directive, .elifdef_without_if);
553 if_level += 1;
554 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
555 } else if (if_level == 1) {
556 guard_name = null;
557 }
558 switch (std.mem.readPackedIntNative(u2, &if_kind, if_level * 2)) {
559 until_else => {
560 const macro_name = try pp.expectMacroName(&tokenizer);
561 if (macro_name == null) {
562 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
563 try pp.skip(&tokenizer, .until_else);
564 if (pp.verbose) {
565 pp.verboseLog(directive, "entering else branch of #elifndef", .{});
566 }
567 } else {
568 try pp.expectNl(&tokenizer);
569 if (pp.defines.get(macro_name.?) == null) {
570 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
571 if (pp.verbose) {
572 pp.verboseLog(directive, "entering then branch of #elifndef", .{});
573 }
574 } else {
575 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
576 try pp.skip(&tokenizer, .until_else);
577 if (pp.verbose) {
578 pp.verboseLog(directive, "entering else branch of #elifndef", .{});
579 }
580 }
581 }
582 },
583 until_endif => try pp.skip(&tokenizer, .until_endif),
584 until_endif_seen_else => {
585 try pp.err(directive, .elifdef_after_else);
586 skipToNl(&tokenizer);
587 },
588 else => unreachable,
589 }
590 },
591 .keyword_else => {
592 try pp.expectNl(&tokenizer);
593 if (if_level == 0) {
594 try pp.err(directive, .else_without_if);
595 continue;
596 } else if (if_level == 1) {
597 guard_name = null;
598 }
599 switch (std.mem.readPackedIntNative(u2, &if_kind, if_level * 2)) {
600 until_else => {
601 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif_seen_else);
602 if (pp.verbose) {
603 pp.verboseLog(directive, "#else branch here", .{});
604 }
605 },
606 until_endif => try pp.skip(&tokenizer, .until_endif_seen_else),
607 until_endif_seen_else => {
608 try pp.err(directive, .else_after_else);
609 skipToNl(&tokenizer);
610 },
611 else => unreachable,
612 }
613 },
614 .keyword_endif => {
615 try pp.expectNl(&tokenizer);
616 if (if_level == 0) {
617 guard_name = null;
618 try pp.err(directive, .endif_without_if);
619 continue;
620 } else if (if_level == 1) {
621 const saved_tokenizer = tokenizer;
622 defer tokenizer = saved_tokenizer;
623
624 var next = tokenizer.nextNoWS();
625 while (next.id == .nl) : (next = tokenizer.nextNoWS()) {}
626 if (next.id != .eof) guard_name = null;
627 }
628 if_level -= 1;
629 },
630 .keyword_define => try pp.define(&tokenizer, directive),
631 .keyword_undef => {
632 const macro_name = (try pp.expectMacroName(&tokenizer)) orelse continue;
633 if (pp.store_macro_tokens) {
634 try pp.addToken(tokFromRaw(directive));
635 }
636
637 _ = pp.defines.remove(macro_name);
638 try pp.expectNl(&tokenizer);
639 },
640 .keyword_include => {
641 try pp.include(&tokenizer, .first);
642 continue;
643 },
644 .keyword_include_next => {
645 try pp.comp.addDiagnostic(.{
646 .tag = .include_next,
647 .loc = .{ .id = tok.source, .byte_offset = directive.start, .line = directive.line },
648 }, &.{});
649 if (pp.include_depth == 0) {
650 try pp.comp.addDiagnostic(.{
651 .tag = .include_next_outside_header,
652 .loc = .{ .id = tok.source, .byte_offset = directive.start, .line = directive.line },
653 }, &.{});
654 try pp.include(&tokenizer, .first);
655 } else {
656 try pp.include(&tokenizer, .next);
657 }
658 },
659 .keyword_embed => try pp.embed(&tokenizer),
660 .keyword_pragma => {
661 try pp.pragma(&tokenizer, directive, null, &.{});
662 continue;
663 },
664 .keyword_line => {
665 // #line number "file"
666 const digits = tokenizer.nextNoWS();
667 if (digits.id != .pp_num) try pp.err(digits, .line_simple_digit);
668 // TODO: validate that the pp_num token is solely digits
669
670 if (digits.id == .eof or digits.id == .nl) continue;
671 const name = tokenizer.nextNoWS();
672 if (name.id == .eof or name.id == .nl) continue;
673 if (name.id != .string_literal) try pp.err(name, .line_invalid_filename);
674 try pp.expectNl(&tokenizer);
675 },
676 .pp_num => {
677 // # number "file" flags
678 // TODO: validate that the pp_num token is solely digits
679 // if not, emit `GNU line marker directive requires a simple digit sequence`
680 const name = tokenizer.nextNoWS();
681 if (name.id == .eof or name.id == .nl) continue;
682 if (name.id != .string_literal) try pp.err(name, .line_invalid_filename);
683
684 const flag_1 = tokenizer.nextNoWS();
685 if (flag_1.id == .eof or flag_1.id == .nl) continue;
686 const flag_2 = tokenizer.nextNoWS();
687 if (flag_2.id == .eof or flag_2.id == .nl) continue;
688 const flag_3 = tokenizer.nextNoWS();
689 if (flag_3.id == .eof or flag_3.id == .nl) continue;
690 const flag_4 = tokenizer.nextNoWS();
691 if (flag_4.id == .eof or flag_4.id == .nl) continue;
692 try pp.expectNl(&tokenizer);
693 },
694 .nl => {},
695 .eof => {
696 if (if_level != 0) try pp.err(tok, .unterminated_conditional_directive);
697 return tokFromRaw(directive);
698 },
699 else => {
700 try pp.err(tok, .invalid_preprocessing_directive);
701 skipToNl(&tokenizer);
702 },
703 }
704 if (pp.preserve_whitespace) {
705 tok.id = .nl;
706 try pp.addToken(tokFromRaw(tok));
707 }
708 },
709 .whitespace => if (pp.preserve_whitespace) try pp.addToken(tokFromRaw(tok)),
710 .nl => {
711 start_of_line = true;
712 if (pp.preserve_whitespace) try pp.addToken(tokFromRaw(tok));
713 },
714 .eof => {
715 if (if_level != 0) try pp.err(tok, .unterminated_conditional_directive);
716 // The following check needs to occur here and not at the top of the function
717 // because a pragma may change the level during preprocessing
718 if (source.buf.len > 0 and source.buf[source.buf.len - 1] != '\n') {
719 try pp.err(tok, .newline_eof);
720 }
721 if (guard_name) |name| {
722 if (try pp.include_guards.fetchPut(pp.gpa, source.id, name)) |prev| {
723 assert(mem.eql(u8, name, prev.value));
724 }
725 }
726 return tokFromRaw(tok);
727 },
728 .unterminated_string_literal, .unterminated_char_literal, .empty_char_literal => |tag| {
729 start_of_line = false;
730 try pp.err(tok, invalidTokenDiagnostic(tag));
731 try pp.expandMacro(&tokenizer, tok);
732 },
733 .unterminated_comment => try pp.err(tok, .unterminated_comment),
734 else => {
735 if (tok.id.isMacroIdentifier() and pp.poisoned_identifiers.get(pp.tokSlice(tok)) != null) {
736 try pp.err(tok, .poisoned_identifier);
737 }
738 // Add the token to the buffer doing any necessary expansions.
739 start_of_line = false;
740 try pp.expandMacro(&tokenizer, tok);
741 },
742 }
743 }
744}
745
746/// Get raw token source string.
747/// Returned slice is invalidated when comp.generated_buf is updated.
748pub fn tokSlice(pp: *Preprocessor, token: anytype) []const u8 {
749 if (token.id.lexeme()) |some| return some;
750 const source = pp.comp.getSource(token.source);
751 return source.buf[token.start..token.end];
752}
753
754/// Convert a token from the Tokenizer into a token used by the parser.
755fn tokFromRaw(raw: RawToken) TokenWithExpansionLocs {
756 return .{
757 .id = raw.id,
758 .loc = .{
759 .id = raw.source,
760 .byte_offset = raw.start,
761 .line = raw.line,
762 },
763 };
764}
765
766fn err(pp: *Preprocessor, raw: RawToken, tag: Diagnostics.Tag) !void {
767 try pp.comp.addDiagnostic(.{
768 .tag = tag,
769 .loc = .{
770 .id = raw.source,
771 .byte_offset = raw.start,
772 .line = raw.line,
773 },
774 }, &.{});
775}
776
777fn errStr(pp: *Preprocessor, tok: TokenWithExpansionLocs, tag: Diagnostics.Tag, str: []const u8) !void {
778 try pp.comp.addDiagnostic(.{
779 .tag = tag,
780 .loc = tok.loc,
781 .extra = .{ .str = str },
782 }, tok.expansionSlice());
783}
784
785fn fatal(pp: *Preprocessor, raw: RawToken, comptime fmt: []const u8, args: anytype) Compilation.Error {
786 try pp.comp.diagnostics.list.append(pp.gpa, .{
787 .tag = .cli_error,
788 .kind = .@"fatal error",
789 .extra = .{ .str = try std.fmt.allocPrint(pp.comp.diagnostics.arena.allocator(), fmt, args) },
790 .loc = .{
791 .id = raw.source,
792 .byte_offset = raw.start,
793 .line = raw.line,
794 },
795 });
796 return error.FatalError;
797}
798
799fn fatalNotFound(pp: *Preprocessor, tok: TokenWithExpansionLocs, filename: []const u8) Compilation.Error {
800 const old = pp.comp.diagnostics.fatal_errors;
801 pp.comp.diagnostics.fatal_errors = true;
802 defer pp.comp.diagnostics.fatal_errors = old;
803
804 try pp.comp.diagnostics.addExtra(pp.comp.langopts, .{ .tag = .cli_error, .loc = tok.loc, .extra = .{
805 .str = try std.fmt.allocPrint(pp.comp.diagnostics.arena.allocator(), "'{s}' not found", .{filename}),
806 } }, tok.expansionSlice(), false);
807 unreachable; // addExtra should've returned FatalError
808}
809
810fn verboseLog(pp: *Preprocessor, raw: RawToken, comptime fmt: []const u8, args: anytype) void {
811 const source = pp.comp.getSource(raw.source);
812 const line_col = source.lineCol(.{ .id = raw.source, .line = raw.line, .byte_offset = raw.start });
813
814 const stderr = std.io.getStdErr().writer();
815 var buf_writer = std.io.bufferedWriter(stderr);
816 const writer = buf_writer.writer();
817 defer buf_writer.flush() catch {};
818 writer.print("{s}:{d}:{d}: ", .{ source.path, line_col.line_no, line_col.col }) catch return;
819 writer.print(fmt, args) catch return;
820 writer.writeByte('\n') catch return;
821 writer.writeAll(line_col.line) catch return;
822 writer.writeByte('\n') catch return;
823}
824
825/// Consume next token, error if it is not an identifier.
826fn expectMacroName(pp: *Preprocessor, tokenizer: *Tokenizer) Error!?[]const u8 {
827 const macro_name = tokenizer.nextNoWS();
828 if (!macro_name.id.isMacroIdentifier()) {
829 try pp.err(macro_name, .macro_name_missing);
830 skipToNl(tokenizer);
831 return null;
832 }
833 return pp.tokSlice(macro_name);
834}
835
836/// Skip until after a newline, error if extra tokens before it.
837fn expectNl(pp: *Preprocessor, tokenizer: *Tokenizer) Error!void {
838 var sent_err = false;
839 while (true) {
840 const tok = tokenizer.next();
841 if (tok.id == .nl or tok.id == .eof) return;
842 if (tok.id == .whitespace or tok.id == .comment) continue;
843 if (!sent_err) {
844 sent_err = true;
845 try pp.err(tok, .extra_tokens_directive_end);
846 }
847 }
848}
849
850fn getTokenState(pp: *const Preprocessor) TokenState {
851 return .{
852 .tokens_len = pp.tokens.len,
853 .expansion_entries_len = pp.expansion_entries.len,
854 };
855}
856
857fn restoreTokenState(pp: *Preprocessor, state: TokenState) void {
858 pp.tokens.len = state.tokens_len;
859 pp.expansion_entries.len = state.expansion_entries_len;
860}
861
862/// Consume all tokens until a newline and parse the result into a boolean.
863fn expr(pp: *Preprocessor, tokenizer: *Tokenizer) MacroError!bool {
864 const token_state = pp.getTokenState();
865 defer {
866 for (pp.top_expansion_buf.items) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
867 pp.restoreTokenState(token_state);
868 }
869
870 pp.top_expansion_buf.items.len = 0;
871 const eof = while (true) {
872 const tok = tokenizer.next();
873 switch (tok.id) {
874 .nl, .eof => break tok,
875 .whitespace => if (pp.top_expansion_buf.items.len == 0) continue,
876 else => {},
877 }
878 try pp.top_expansion_buf.append(tokFromRaw(tok));
879 } else unreachable;
880 if (pp.top_expansion_buf.items.len != 0) {
881 pp.expansion_source_loc = pp.top_expansion_buf.items[0].loc;
882 pp.hideset.clearRetainingCapacity();
883 try pp.expandMacroExhaustive(tokenizer, &pp.top_expansion_buf, 0, pp.top_expansion_buf.items.len, false, .expr);
884 }
885 for (pp.top_expansion_buf.items) |tok| {
886 if (tok.id == .macro_ws) continue;
887 if (!tok.id.validPreprocessorExprStart()) {
888 try pp.comp.addDiagnostic(.{
889 .tag = .invalid_preproc_expr_start,
890 .loc = tok.loc,
891 }, tok.expansionSlice());
892 return false;
893 }
894 break;
895 } else {
896 try pp.err(eof, .expected_value_in_expr);
897 return false;
898 }
899
900 // validate the tokens in the expression
901 try pp.ensureUnusedTokenCapacity(pp.top_expansion_buf.items.len);
902 var i: usize = 0;
903 const items = pp.top_expansion_buf.items;
904 while (i < items.len) : (i += 1) {
905 var tok = items[i];
906 switch (tok.id) {
907 .string_literal,
908 .string_literal_utf_16,
909 .string_literal_utf_8,
910 .string_literal_utf_32,
911 .string_literal_wide,
912 => {
913 try pp.comp.addDiagnostic(.{
914 .tag = .string_literal_in_pp_expr,
915 .loc = tok.loc,
916 }, tok.expansionSlice());
917 return false;
918 },
919 .plus_plus,
920 .minus_minus,
921 .plus_equal,
922 .minus_equal,
923 .asterisk_equal,
924 .slash_equal,
925 .percent_equal,
926 .angle_bracket_angle_bracket_left_equal,
927 .angle_bracket_angle_bracket_right_equal,
928 .ampersand_equal,
929 .caret_equal,
930 .pipe_equal,
931 .l_bracket,
932 .r_bracket,
933 .l_brace,
934 .r_brace,
935 .ellipsis,
936 .semicolon,
937 .hash,
938 .hash_hash,
939 .equal,
940 .arrow,
941 .period,
942 => {
943 try pp.comp.addDiagnostic(.{
944 .tag = .invalid_preproc_operator,
945 .loc = tok.loc,
946 }, tok.expansionSlice());
947 return false;
948 },
949 .macro_ws, .whitespace => continue,
950 .keyword_false => tok.id = .zero,
951 .keyword_true => tok.id = .one,
952 else => if (tok.id.isMacroIdentifier()) {
953 if (tok.id == .keyword_defined) {
954 const tokens_consumed = try pp.handleKeywordDefined(&tok, items[i + 1 ..], eof);
955 i += tokens_consumed;
956 } else {
957 try pp.errStr(tok, .undefined_macro, pp.expandedSlice(tok));
958
959 if (i + 1 < pp.top_expansion_buf.items.len and
960 pp.top_expansion_buf.items[i + 1].id == .l_paren)
961 {
962 try pp.errStr(tok, .fn_macro_undefined, pp.expandedSlice(tok));
963 return false;
964 }
965
966 tok.id = .zero; // undefined macro
967 }
968 },
969 }
970 pp.addTokenAssumeCapacity(tok);
971 }
972 try pp.addToken(.{
973 .id = .eof,
974 .loc = tokFromRaw(eof).loc,
975 });
976
977 // Actually parse it.
978 var parser = Parser{
979 .pp = pp,
980 .comp = pp.comp,
981 .gpa = pp.gpa,
982 .tok_ids = pp.tokens.items(.id),
983 .tok_i = @intCast(token_state.tokens_len),
984 .arena = pp.arena.allocator(),
985 .in_macro = true,
986 .strings = std.ArrayListAligned(u8, 4).init(pp.comp.gpa),
987
988 .data = undefined,
989 .value_map = undefined,
990 .labels = undefined,
991 .decl_buf = undefined,
992 .list_buf = undefined,
993 .param_buf = undefined,
994 .enum_buf = undefined,
995 .record_buf = undefined,
996 .attr_buf = undefined,
997 .field_attr_buf = undefined,
998 .string_ids = undefined,
999 };
1000 defer parser.strings.deinit();
1001 return parser.macroExpr();
1002}
1003
1004/// Turns macro_tok from .keyword_defined into .zero or .one depending on whether the argument is defined
1005/// Returns the number of tokens consumed
1006fn handleKeywordDefined(pp: *Preprocessor, macro_tok: *TokenWithExpansionLocs, tokens: []const TokenWithExpansionLocs, eof: RawToken) !usize {
1007 std.debug.assert(macro_tok.id == .keyword_defined);
1008 var it = TokenIterator.init(tokens);
1009 const first = it.nextNoWS() orelse {
1010 try pp.err(eof, .macro_name_missing);
1011 return it.i;
1012 };
1013 switch (first.id) {
1014 .l_paren => {},
1015 else => {
1016 if (!first.id.isMacroIdentifier()) {
1017 try pp.errStr(first, .macro_name_must_be_identifier, pp.expandedSlice(first));
1018 }
1019 macro_tok.id = if (pp.defines.contains(pp.expandedSlice(first))) .one else .zero;
1020 return it.i;
1021 },
1022 }
1023 const second = it.nextNoWS() orelse {
1024 try pp.err(eof, .macro_name_missing);
1025 return it.i;
1026 };
1027 if (!second.id.isMacroIdentifier()) {
1028 try pp.comp.addDiagnostic(.{
1029 .tag = .macro_name_must_be_identifier,
1030 .loc = second.loc,
1031 }, second.expansionSlice());
1032 return it.i;
1033 }
1034 macro_tok.id = if (pp.defines.contains(pp.expandedSlice(second))) .one else .zero;
1035
1036 const last = it.nextNoWS();
1037 if (last == null or last.?.id != .r_paren) {
1038 const tok = last orelse tokFromRaw(eof);
1039 try pp.comp.addDiagnostic(.{
1040 .tag = .closing_paren,
1041 .loc = tok.loc,
1042 }, tok.expansionSlice());
1043 try pp.comp.addDiagnostic(.{
1044 .tag = .to_match_paren,
1045 .loc = first.loc,
1046 }, first.expansionSlice());
1047 }
1048
1049 return it.i;
1050}
1051
1052/// Skip until #else #elif #endif, return last directive token id.
1053/// Also skips nested #if ... #endifs.
1054fn skip(
1055 pp: *Preprocessor,
1056 tokenizer: *Tokenizer,
1057 cont: enum { until_else, until_endif, until_endif_seen_else },
1058) Error!void {
1059 var ifs_seen: u32 = 0;
1060 var line_start = true;
1061 while (tokenizer.index < tokenizer.buf.len) {
1062 if (line_start) {
1063 const saved_tokenizer = tokenizer.*;
1064 const hash = tokenizer.nextNoWS();
1065 if (hash.id == .nl) continue;
1066 line_start = false;
1067 if (hash.id != .hash) continue;
1068 const directive = tokenizer.nextNoWS();
1069 switch (directive.id) {
1070 .keyword_else => {
1071 if (ifs_seen != 0) continue;
1072 if (cont == .until_endif_seen_else) {
1073 try pp.err(directive, .else_after_else);
1074 continue;
1075 }
1076 tokenizer.* = saved_tokenizer;
1077 return;
1078 },
1079 .keyword_elif => {
1080 if (ifs_seen != 0 or cont == .until_endif) continue;
1081 if (cont == .until_endif_seen_else) {
1082 try pp.err(directive, .elif_after_else);
1083 continue;
1084 }
1085 tokenizer.* = saved_tokenizer;
1086 return;
1087 },
1088 .keyword_elifdef => {
1089 if (ifs_seen != 0 or cont == .until_endif) continue;
1090 if (cont == .until_endif_seen_else) {
1091 try pp.err(directive, .elifdef_after_else);
1092 continue;
1093 }
1094 tokenizer.* = saved_tokenizer;
1095 return;
1096 },
1097 .keyword_elifndef => {
1098 if (ifs_seen != 0 or cont == .until_endif) continue;
1099 if (cont == .until_endif_seen_else) {
1100 try pp.err(directive, .elifndef_after_else);
1101 continue;
1102 }
1103 tokenizer.* = saved_tokenizer;
1104 return;
1105 },
1106 .keyword_endif => {
1107 if (ifs_seen == 0) {
1108 tokenizer.* = saved_tokenizer;
1109 return;
1110 }
1111 ifs_seen -= 1;
1112 },
1113 .keyword_if, .keyword_ifdef, .keyword_ifndef => ifs_seen += 1,
1114 else => {},
1115 }
1116 } else if (tokenizer.buf[tokenizer.index] == '\n') {
1117 line_start = true;
1118 tokenizer.index += 1;
1119 tokenizer.line += 1;
1120 if (pp.preserve_whitespace) {
1121 try pp.addToken(.{ .id = .nl, .loc = .{
1122 .id = tokenizer.source,
1123 .line = tokenizer.line,
1124 } });
1125 }
1126 } else {
1127 line_start = false;
1128 tokenizer.index += 1;
1129 }
1130 } else {
1131 const eof = tokenizer.next();
1132 return pp.err(eof, .unterminated_conditional_directive);
1133 }
1134}
1135
1136// Skip until newline, ignore other tokens.
1137fn skipToNl(tokenizer: *Tokenizer) void {
1138 while (true) {
1139 const tok = tokenizer.next();
1140 if (tok.id == .nl or tok.id == .eof) return;
1141 }
1142}
1143
1144const ExpandBuf = std.ArrayList(TokenWithExpansionLocs);
1145fn removePlacemarkers(buf: *ExpandBuf) void {
1146 var i: usize = buf.items.len -% 1;
1147 while (i < buf.items.len) : (i -%= 1) {
1148 if (buf.items[i].id == .placemarker) {
1149 const placemarker = buf.orderedRemove(i);
1150 TokenWithExpansionLocs.free(placemarker.expansion_locs, buf.allocator);
1151 }
1152 }
1153}
1154
1155const MacroArguments = std.ArrayList([]const TokenWithExpansionLocs);
1156fn deinitMacroArguments(allocator: Allocator, args: *const MacroArguments) void {
1157 for (args.items) |item| {
1158 for (item) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, allocator);
1159 allocator.free(item);
1160 }
1161 args.deinit();
1162}
1163
1164fn expandObjMacro(pp: *Preprocessor, simple_macro: *const Macro) Error!ExpandBuf {
1165 var buf = ExpandBuf.init(pp.gpa);
1166 errdefer buf.deinit();
1167 if (simple_macro.tokens.len == 0) {
1168 try buf.append(.{ .id = .placemarker, .loc = .{ .id = .generated } });
1169 return buf;
1170 }
1171 try buf.ensureTotalCapacity(simple_macro.tokens.len);
1172
1173 // Add all of the simple_macros tokens to the new buffer handling any concats.
1174 var i: usize = 0;
1175 while (i < simple_macro.tokens.len) : (i += 1) {
1176 const raw = simple_macro.tokens[i];
1177 const tok = tokFromRaw(raw);
1178 switch (raw.id) {
1179 .hash_hash => {
1180 var rhs = tokFromRaw(simple_macro.tokens[i + 1]);
1181 i += 1;
1182 while (true) {
1183 if (rhs.id == .whitespace) {
1184 rhs = tokFromRaw(simple_macro.tokens[i + 1]);
1185 i += 1;
1186 } else if (rhs.id == .comment and !pp.comp.langopts.preserve_comments_in_macros) {
1187 rhs = tokFromRaw(simple_macro.tokens[i + 1]);
1188 i += 1;
1189 } else break;
1190 }
1191 try pp.pasteTokens(&buf, &.{rhs});
1192 },
1193 .whitespace => if (pp.preserve_whitespace) buf.appendAssumeCapacity(tok),
1194 .macro_file => {
1195 const start = pp.comp.generated_buf.items.len;
1196 const source = pp.comp.getSource(pp.expansion_source_loc.id);
1197 const w = pp.comp.generated_buf.writer(pp.gpa);
1198 try w.print("\"{s}\"\n", .{source.path});
1199
1200 buf.appendAssumeCapacity(try pp.makeGeneratedToken(start, .string_literal, tok));
1201 },
1202 .macro_line => {
1203 const start = pp.comp.generated_buf.items.len;
1204 const source = pp.comp.getSource(pp.expansion_source_loc.id);
1205 const w = pp.comp.generated_buf.writer(pp.gpa);
1206 try w.print("{d}\n", .{source.physicalLine(pp.expansion_source_loc)});
1207
1208 buf.appendAssumeCapacity(try pp.makeGeneratedToken(start, .pp_num, tok));
1209 },
1210 .macro_counter => {
1211 defer pp.counter += 1;
1212 const start = pp.comp.generated_buf.items.len;
1213 const w = pp.comp.generated_buf.writer(pp.gpa);
1214 try w.print("{d}\n", .{pp.counter});
1215
1216 buf.appendAssumeCapacity(try pp.makeGeneratedToken(start, .pp_num, tok));
1217 },
1218 else => buf.appendAssumeCapacity(tok),
1219 }
1220 }
1221
1222 return buf;
1223}
1224
1225/// Join a possibly-parenthesized series of string literal tokens into a single string without
1226/// leading or trailing quotes. The returned slice is invalidated if pp.char_buf changes.
1227/// Returns error.ExpectedStringLiteral if parentheses are not balanced, a non-string-literal
1228/// is encountered, or if no string literals are encountered
1229/// TODO: destringize (replace all '\\' with a single `\` and all '\"' with a '"')
1230fn pasteStringsUnsafe(pp: *Preprocessor, toks: []const TokenWithExpansionLocs) ![]const u8 {
1231 const char_top = pp.char_buf.items.len;
1232 defer pp.char_buf.items.len = char_top;
1233 var unwrapped = toks;
1234 if (toks.len >= 2 and toks[0].id == .l_paren and toks[toks.len - 1].id == .r_paren) {
1235 unwrapped = toks[1 .. toks.len - 1];
1236 }
1237 if (unwrapped.len == 0) return error.ExpectedStringLiteral;
1238
1239 for (unwrapped) |tok| {
1240 if (tok.id == .macro_ws) continue;
1241 if (tok.id != .string_literal) return error.ExpectedStringLiteral;
1242 const str = pp.expandedSlice(tok);
1243 try pp.char_buf.appendSlice(str[1 .. str.len - 1]);
1244 }
1245 return pp.char_buf.items[char_top..];
1246}
1247
1248/// Handle the _Pragma operator (implemented as a builtin macro)
1249fn pragmaOperator(pp: *Preprocessor, arg_tok: TokenWithExpansionLocs, operator_loc: Source.Location) !void {
1250 const arg_slice = pp.expandedSlice(arg_tok);
1251 const content = arg_slice[1 .. arg_slice.len - 1];
1252 const directive = "#pragma ";
1253
1254 pp.char_buf.clearRetainingCapacity();
1255 const total_len = directive.len + content.len + 1; // destringify can never grow the string, + 1 for newline
1256 try pp.char_buf.ensureUnusedCapacity(total_len);
1257 pp.char_buf.appendSliceAssumeCapacity(directive);
1258 pp.destringify(content);
1259 pp.char_buf.appendAssumeCapacity('\n');
1260
1261 const start = pp.comp.generated_buf.items.len;
1262 try pp.comp.generated_buf.appendSlice(pp.gpa, pp.char_buf.items);
1263 var tmp_tokenizer = Tokenizer{
1264 .buf = pp.comp.generated_buf.items,
1265 .langopts = pp.comp.langopts,
1266 .index = @intCast(start),
1267 .source = .generated,
1268 .line = pp.generated_line,
1269 };
1270 pp.generated_line += 1;
1271 const hash_tok = tmp_tokenizer.next();
1272 assert(hash_tok.id == .hash);
1273 const pragma_tok = tmp_tokenizer.next();
1274 assert(pragma_tok.id == .keyword_pragma);
1275 try pp.pragma(&tmp_tokenizer, pragma_tok, operator_loc, arg_tok.expansionSlice());
1276}
1277
1278/// Inverts the output of the preprocessor stringify (#) operation
1279/// (except all whitespace is condensed to a single space)
1280/// writes output to pp.char_buf; assumes capacity is sufficient
1281/// backslash backslash -> backslash
1282/// backslash doublequote -> doublequote
1283/// All other characters remain the same
1284fn destringify(pp: *Preprocessor, str: []const u8) void {
1285 var state: enum { start, backslash_seen } = .start;
1286 for (str) |c| {
1287 switch (c) {
1288 '\\' => {
1289 if (state == .backslash_seen) pp.char_buf.appendAssumeCapacity(c);
1290 state = if (state == .start) .backslash_seen else .start;
1291 },
1292 else => {
1293 if (state == .backslash_seen and c != '"') pp.char_buf.appendAssumeCapacity('\\');
1294 pp.char_buf.appendAssumeCapacity(c);
1295 state = .start;
1296 },
1297 }
1298 }
1299}
1300
1301/// Stringify `tokens` into pp.char_buf.
1302/// See https://gcc.gnu.org/onlinedocs/gcc-11.2.0/cpp/Stringizing.html#Stringizing
1303fn stringify(pp: *Preprocessor, tokens: []const TokenWithExpansionLocs) !void {
1304 try pp.char_buf.append('"');
1305 var ws_state: enum { start, need, not_needed } = .start;
1306 for (tokens) |tok| {
1307 if (tok.id == .macro_ws) {
1308 if (ws_state == .start) continue;
1309 ws_state = .need;
1310 continue;
1311 }
1312 if (ws_state == .need) try pp.char_buf.append(' ');
1313 ws_state = .not_needed;
1314
1315 // backslashes not inside strings are not escaped
1316 const is_str = switch (tok.id) {
1317 .string_literal,
1318 .string_literal_utf_16,
1319 .string_literal_utf_8,
1320 .string_literal_utf_32,
1321 .string_literal_wide,
1322 .char_literal,
1323 .char_literal_utf_16,
1324 .char_literal_utf_32,
1325 .char_literal_wide,
1326 => true,
1327 else => false,
1328 };
1329
1330 for (pp.expandedSlice(tok)) |c| {
1331 if (c == '"')
1332 try pp.char_buf.appendSlice("\\\"")
1333 else if (c == '\\' and is_str)
1334 try pp.char_buf.appendSlice("\\\\")
1335 else
1336 try pp.char_buf.append(c);
1337 }
1338 }
1339 try pp.char_buf.ensureUnusedCapacity(2);
1340 if (pp.char_buf.items[pp.char_buf.items.len - 1] != '\\') {
1341 pp.char_buf.appendSliceAssumeCapacity("\"\n");
1342 return;
1343 }
1344 pp.char_buf.appendAssumeCapacity('"');
1345 var tokenizer: Tokenizer = .{
1346 .buf = pp.char_buf.items,
1347 .index = 0,
1348 .source = .generated,
1349 .langopts = pp.comp.langopts,
1350 .line = 0,
1351 };
1352 const item = tokenizer.next();
1353 if (item.id == .unterminated_string_literal) {
1354 const tok = tokens[tokens.len - 1];
1355 try pp.comp.addDiagnostic(.{
1356 .tag = .invalid_pp_stringify_escape,
1357 .loc = tok.loc,
1358 }, tok.expansionSlice());
1359 pp.char_buf.items.len -= 2; // erase unpaired backslash and appended end quote
1360 pp.char_buf.appendAssumeCapacity('"');
1361 }
1362 pp.char_buf.appendAssumeCapacity('\n');
1363}
1364
1365fn reconstructIncludeString(pp: *Preprocessor, param_toks: []const TokenWithExpansionLocs, embed_args: ?*[]const TokenWithExpansionLocs, first: TokenWithExpansionLocs) !?[]const u8 {
1366 if (param_toks.len == 0) {
1367 try pp.comp.addDiagnostic(.{
1368 .tag = .expected_filename,
1369 .loc = first.loc,
1370 }, first.expansionSlice());
1371 return null;
1372 }
1373
1374 const char_top = pp.char_buf.items.len;
1375 defer pp.char_buf.items.len = char_top;
1376
1377 // Trim leading/trailing whitespace
1378 var begin: usize = 0;
1379 var end: usize = param_toks.len;
1380 while (begin < end and param_toks[begin].id == .macro_ws) : (begin += 1) {}
1381 while (end > begin and param_toks[end - 1].id == .macro_ws) : (end -= 1) {}
1382 const params = param_toks[begin..end];
1383
1384 if (params.len == 0) {
1385 try pp.comp.addDiagnostic(.{
1386 .tag = .expected_filename,
1387 .loc = first.loc,
1388 }, first.expansionSlice());
1389 return null;
1390 }
1391 // no string pasting
1392 if (embed_args == null and params[0].id == .string_literal and params.len > 1) {
1393 try pp.comp.addDiagnostic(.{
1394 .tag = .closing_paren,
1395 .loc = params[1].loc,
1396 }, params[1].expansionSlice());
1397 return null;
1398 }
1399
1400 for (params, 0..) |tok, i| {
1401 const str = pp.expandedSliceExtra(tok, .preserve_macro_ws);
1402 try pp.char_buf.appendSlice(str);
1403 if (embed_args) |some| {
1404 if ((i == 0 and tok.id == .string_literal) or tok.id == .angle_bracket_right) {
1405 some.* = params[i + 1 ..];
1406 break;
1407 }
1408 }
1409 }
1410
1411 const include_str = pp.char_buf.items[char_top..];
1412 if (include_str.len < 3) {
1413 if (include_str.len == 0) {
1414 try pp.comp.addDiagnostic(.{
1415 .tag = .expected_filename,
1416 .loc = first.loc,
1417 }, first.expansionSlice());
1418 return null;
1419 }
1420 try pp.comp.addDiagnostic(.{
1421 .tag = .empty_filename,
1422 .loc = params[0].loc,
1423 }, params[0].expansionSlice());
1424 return null;
1425 }
1426
1427 switch (include_str[0]) {
1428 '<' => {
1429 if (include_str[include_str.len - 1] != '>') {
1430 // Ugly hack to find out where the '>' should go, since we don't have the closing ')' location
1431 const start = params[0].loc;
1432 try pp.comp.addDiagnostic(.{
1433 .tag = .header_str_closing,
1434 .loc = .{ .id = start.id, .byte_offset = start.byte_offset + @as(u32, @intCast(include_str.len)) + 1, .line = start.line },
1435 }, params[0].expansionSlice());
1436 try pp.comp.addDiagnostic(.{
1437 .tag = .header_str_match,
1438 .loc = params[0].loc,
1439 }, params[0].expansionSlice());
1440 return null;
1441 }
1442 return include_str;
1443 },
1444 '"' => return include_str,
1445 else => {
1446 try pp.comp.addDiagnostic(.{
1447 .tag = .expected_filename,
1448 .loc = params[0].loc,
1449 }, params[0].expansionSlice());
1450 return null;
1451 },
1452 }
1453}
1454
1455fn handleBuiltinMacro(pp: *Preprocessor, builtin: RawToken.Id, param_toks: []const TokenWithExpansionLocs, src_loc: Source.Location) Error!bool {
1456 switch (builtin) {
1457 .macro_param_has_attribute,
1458 .macro_param_has_declspec_attribute,
1459 .macro_param_has_feature,
1460 .macro_param_has_extension,
1461 .macro_param_has_builtin,
1462 => {
1463 var invalid: ?TokenWithExpansionLocs = null;
1464 var identifier: ?TokenWithExpansionLocs = null;
1465 for (param_toks) |tok| {
1466 if (tok.id == .macro_ws) continue;
1467 if (tok.id == .comment) continue;
1468 if (!tok.id.isMacroIdentifier()) {
1469 invalid = tok;
1470 break;
1471 }
1472 if (identifier) |_| invalid = tok else identifier = tok;
1473 }
1474 if (identifier == null and invalid == null) invalid = .{ .id = .eof, .loc = src_loc };
1475 if (invalid) |some| {
1476 try pp.comp.addDiagnostic(
1477 .{ .tag = .feature_check_requires_identifier, .loc = some.loc },
1478 some.expansionSlice(),
1479 );
1480 return false;
1481 }
1482
1483 const ident_str = pp.expandedSlice(identifier.?);
1484 return switch (builtin) {
1485 .macro_param_has_attribute => Attribute.fromString(.gnu, null, ident_str) != null,
1486 .macro_param_has_declspec_attribute => {
1487 return if (pp.comp.langopts.declspec_attrs)
1488 Attribute.fromString(.declspec, null, ident_str) != null
1489 else
1490 false;
1491 },
1492 .macro_param_has_feature => features.hasFeature(pp.comp, ident_str),
1493 .macro_param_has_extension => features.hasExtension(pp.comp, ident_str),
1494 .macro_param_has_builtin => pp.comp.hasBuiltin(ident_str),
1495 else => unreachable,
1496 };
1497 },
1498 .macro_param_has_warning => {
1499 const actual_param = pp.pasteStringsUnsafe(param_toks) catch |er| switch (er) {
1500 error.ExpectedStringLiteral => {
1501 try pp.errStr(param_toks[0], .expected_str_literal_in, "__has_warning");
1502 return false;
1503 },
1504 else => |e| return e,
1505 };
1506 if (!mem.startsWith(u8, actual_param, "-W")) {
1507 try pp.errStr(param_toks[0], .malformed_warning_check, "__has_warning");
1508 return false;
1509 }
1510 const warning_name = actual_param[2..];
1511 return Diagnostics.warningExists(warning_name);
1512 },
1513 .macro_param_is_identifier => {
1514 var invalid: ?TokenWithExpansionLocs = null;
1515 var identifier: ?TokenWithExpansionLocs = null;
1516 for (param_toks) |tok| switch (tok.id) {
1517 .macro_ws => continue,
1518 .comment => continue,
1519 else => {
1520 if (identifier) |_| invalid = tok else identifier = tok;
1521 },
1522 };
1523 if (identifier == null and invalid == null) invalid = .{ .id = .eof, .loc = src_loc };
1524 if (invalid) |some| {
1525 try pp.comp.addDiagnostic(.{
1526 .tag = .missing_tok_builtin,
1527 .loc = some.loc,
1528 .extra = .{ .tok_id_expected = .r_paren },
1529 }, some.expansionSlice());
1530 return false;
1531 }
1532
1533 const id = identifier.?.id;
1534 return id == .identifier or id == .extended_identifier;
1535 },
1536 .macro_param_has_include, .macro_param_has_include_next => {
1537 const include_str = (try pp.reconstructIncludeString(param_toks, null, param_toks[0])) orelse return false;
1538 const include_type: Compilation.IncludeType = switch (include_str[0]) {
1539 '"' => .quotes,
1540 '<' => .angle_brackets,
1541 else => unreachable,
1542 };
1543 const filename = include_str[1 .. include_str.len - 1];
1544 if (builtin == .macro_param_has_include or pp.include_depth == 0) {
1545 if (builtin == .macro_param_has_include_next) {
1546 try pp.comp.addDiagnostic(.{
1547 .tag = .include_next_outside_header,
1548 .loc = src_loc,
1549 }, &.{});
1550 }
1551 return pp.comp.hasInclude(filename, src_loc.id, include_type, .first);
1552 }
1553 return pp.comp.hasInclude(filename, src_loc.id, include_type, .next);
1554 },
1555 else => unreachable,
1556 }
1557}
1558
1559/// Treat whitespace-only paste arguments as empty
1560fn getPasteArgs(args: []const TokenWithExpansionLocs) []const TokenWithExpansionLocs {
1561 for (args) |tok| {
1562 if (tok.id != .macro_ws) return args;
1563 }
1564 return &[1]TokenWithExpansionLocs{.{
1565 .id = .placemarker,
1566 .loc = .{ .id = .generated, .byte_offset = 0, .line = 0 },
1567 }};
1568}
1569
1570fn expandFuncMacro(
1571 pp: *Preprocessor,
1572 macro_tok: TokenWithExpansionLocs,
1573 func_macro: *const Macro,
1574 args: *const MacroArguments,
1575 expanded_args: *const MacroArguments,
1576 hideset_arg: Hideset.Index,
1577) MacroError!ExpandBuf {
1578 var hideset = hideset_arg;
1579 var buf = ExpandBuf.init(pp.gpa);
1580 try buf.ensureTotalCapacity(func_macro.tokens.len);
1581 errdefer buf.deinit();
1582
1583 var expanded_variable_arguments = ExpandBuf.init(pp.gpa);
1584 defer expanded_variable_arguments.deinit();
1585 var variable_arguments = ExpandBuf.init(pp.gpa);
1586 defer variable_arguments.deinit();
1587
1588 if (func_macro.var_args) {
1589 var i: usize = func_macro.params.len;
1590 while (i < expanded_args.items.len) : (i += 1) {
1591 try variable_arguments.appendSlice(args.items[i]);
1592 try expanded_variable_arguments.appendSlice(expanded_args.items[i]);
1593 if (i != expanded_args.items.len - 1) {
1594 const comma = TokenWithExpansionLocs{ .id = .comma, .loc = .{ .id = .generated } };
1595 try variable_arguments.append(comma);
1596 try expanded_variable_arguments.append(comma);
1597 }
1598 }
1599 }
1600
1601 // token concatenation and expansion phase
1602 var tok_i: usize = 0;
1603 while (tok_i < func_macro.tokens.len) : (tok_i += 1) {
1604 const raw = func_macro.tokens[tok_i];
1605 switch (raw.id) {
1606 .hash_hash => while (tok_i + 1 < func_macro.tokens.len) {
1607 const raw_next = func_macro.tokens[tok_i + 1];
1608 tok_i += 1;
1609
1610 var va_opt_buf = ExpandBuf.init(pp.gpa);
1611 defer va_opt_buf.deinit();
1612
1613 const next = switch (raw_next.id) {
1614 .macro_ws => continue,
1615 .hash_hash => continue,
1616 .comment => if (!pp.comp.langopts.preserve_comments_in_macros)
1617 continue
1618 else
1619 &[1]TokenWithExpansionLocs{tokFromRaw(raw_next)},
1620 .macro_param, .macro_param_no_expand => getPasteArgs(args.items[raw_next.end]),
1621 .keyword_va_args => variable_arguments.items,
1622 .keyword_va_opt => blk: {
1623 try pp.expandVaOpt(&va_opt_buf, raw_next, variable_arguments.items.len != 0);
1624 if (va_opt_buf.items.len == 0) break;
1625 break :blk va_opt_buf.items;
1626 },
1627 else => &[1]TokenWithExpansionLocs{tokFromRaw(raw_next)},
1628 };
1629 try pp.pasteTokens(&buf, next);
1630 if (next.len != 0) break;
1631 },
1632 .macro_param_no_expand => {
1633 if (tok_i + 1 < func_macro.tokens.len and func_macro.tokens[tok_i + 1].id == .hash_hash) {
1634 hideset = pp.hideset.get(tokFromRaw(func_macro.tokens[tok_i + 1]).loc);
1635 }
1636 const slice = getPasteArgs(args.items[raw.end]);
1637 const raw_loc = Source.Location{ .id = raw.source, .byte_offset = raw.start, .line = raw.line };
1638 try bufCopyTokens(&buf, slice, &.{raw_loc});
1639 },
1640 .macro_param => {
1641 if (tok_i + 1 < func_macro.tokens.len and func_macro.tokens[tok_i + 1].id == .hash_hash) {
1642 hideset = pp.hideset.get(tokFromRaw(func_macro.tokens[tok_i + 1]).loc);
1643 }
1644 const arg = expanded_args.items[raw.end];
1645 const raw_loc = Source.Location{ .id = raw.source, .byte_offset = raw.start, .line = raw.line };
1646 try bufCopyTokens(&buf, arg, &.{raw_loc});
1647 },
1648 .keyword_va_args => {
1649 const raw_loc = Source.Location{ .id = raw.source, .byte_offset = raw.start, .line = raw.line };
1650 try bufCopyTokens(&buf, expanded_variable_arguments.items, &.{raw_loc});
1651 },
1652 .keyword_va_opt => {
1653 try pp.expandVaOpt(&buf, raw, variable_arguments.items.len != 0);
1654 },
1655 .stringify_param, .stringify_va_args => {
1656 const arg = if (raw.id == .stringify_va_args)
1657 variable_arguments.items
1658 else
1659 args.items[raw.end];
1660
1661 pp.char_buf.clearRetainingCapacity();
1662 try pp.stringify(arg);
1663
1664 const start = pp.comp.generated_buf.items.len;
1665 try pp.comp.generated_buf.appendSlice(pp.gpa, pp.char_buf.items);
1666
1667 try buf.append(try pp.makeGeneratedToken(start, .string_literal, tokFromRaw(raw)));
1668 },
1669 .macro_param_has_attribute,
1670 .macro_param_has_declspec_attribute,
1671 .macro_param_has_warning,
1672 .macro_param_has_feature,
1673 .macro_param_has_extension,
1674 .macro_param_has_builtin,
1675 .macro_param_has_include,
1676 .macro_param_has_include_next,
1677 .macro_param_is_identifier,
1678 => {
1679 const arg = expanded_args.items[0];
1680 const result = if (arg.len == 0) blk: {
1681 const extra = Diagnostics.Message.Extra{ .arguments = .{ .expected = 1, .actual = 0 } };
1682 try pp.comp.addDiagnostic(.{ .tag = .expected_arguments, .loc = macro_tok.loc, .extra = extra }, &.{});
1683 break :blk false;
1684 } else try pp.handleBuiltinMacro(raw.id, arg, macro_tok.loc);
1685 const start = pp.comp.generated_buf.items.len;
1686 const w = pp.comp.generated_buf.writer(pp.gpa);
1687 try w.print("{}\n", .{@intFromBool(result)});
1688 try buf.append(try pp.makeGeneratedToken(start, .pp_num, tokFromRaw(raw)));
1689 },
1690 .macro_param_has_c_attribute => {
1691 const arg = expanded_args.items[0];
1692 const not_found = "0\n";
1693 const result = if (arg.len == 0) blk: {
1694 const extra = Diagnostics.Message.Extra{ .arguments = .{ .expected = 1, .actual = 0 } };
1695 try pp.comp.addDiagnostic(.{ .tag = .expected_arguments, .loc = macro_tok.loc, .extra = extra }, &.{});
1696 break :blk not_found;
1697 } else res: {
1698 var invalid: ?TokenWithExpansionLocs = null;
1699 var vendor_ident: ?TokenWithExpansionLocs = null;
1700 var colon_colon: ?TokenWithExpansionLocs = null;
1701 var attr_ident: ?TokenWithExpansionLocs = null;
1702 for (arg) |tok| {
1703 if (tok.id == .macro_ws) continue;
1704 if (tok.id == .comment) continue;
1705 if (tok.id == .colon_colon) {
1706 if (colon_colon != null or attr_ident == null) {
1707 invalid = tok;
1708 break;
1709 }
1710 vendor_ident = attr_ident;
1711 attr_ident = null;
1712 colon_colon = tok;
1713 continue;
1714 }
1715 if (!tok.id.isMacroIdentifier()) {
1716 invalid = tok;
1717 break;
1718 }
1719 if (attr_ident) |_| {
1720 invalid = tok;
1721 break;
1722 } else attr_ident = tok;
1723 }
1724 if (vendor_ident != null and attr_ident == null) {
1725 invalid = vendor_ident;
1726 } else if (attr_ident == null and invalid == null) {
1727 invalid = .{ .id = .eof, .loc = macro_tok.loc };
1728 }
1729 if (invalid) |some| {
1730 try pp.comp.addDiagnostic(
1731 .{ .tag = .feature_check_requires_identifier, .loc = some.loc },
1732 some.expansionSlice(),
1733 );
1734 break :res not_found;
1735 }
1736 if (vendor_ident) |some| {
1737 const vendor_str = pp.expandedSlice(some);
1738 const attr_str = pp.expandedSlice(attr_ident.?);
1739 const exists = Attribute.fromString(.gnu, vendor_str, attr_str) != null;
1740
1741 const start = pp.comp.generated_buf.items.len;
1742 try pp.comp.generated_buf.appendSlice(pp.gpa, if (exists) "1\n" else "0\n");
1743 try buf.append(try pp.makeGeneratedToken(start, .pp_num, tokFromRaw(raw)));
1744 continue;
1745 }
1746 if (!pp.comp.langopts.standard.atLeast(.c23)) break :res not_found;
1747
1748 const attrs = std.StaticStringMap([]const u8).initComptime(.{
1749 .{ "deprecated", "201904L\n" },
1750 .{ "fallthrough", "201904L\n" },
1751 .{ "maybe_unused", "201904L\n" },
1752 .{ "nodiscard", "202003L\n" },
1753 .{ "noreturn", "202202L\n" },
1754 .{ "_Noreturn", "202202L\n" },
1755 .{ "unsequenced", "202207L\n" },
1756 .{ "reproducible", "202207L\n" },
1757 });
1758
1759 const attr_str = Attribute.normalize(pp.expandedSlice(attr_ident.?));
1760 break :res attrs.get(attr_str) orelse not_found;
1761 };
1762 const start = pp.comp.generated_buf.items.len;
1763 try pp.comp.generated_buf.appendSlice(pp.gpa, result);
1764 try buf.append(try pp.makeGeneratedToken(start, .pp_num, tokFromRaw(raw)));
1765 },
1766 .macro_param_has_embed => {
1767 const arg = expanded_args.items[0];
1768 const not_found = "0\n";
1769 const result = if (arg.len == 0) blk: {
1770 const extra = Diagnostics.Message.Extra{ .arguments = .{ .expected = 1, .actual = 0 } };
1771 try pp.comp.addDiagnostic(.{ .tag = .expected_arguments, .loc = macro_tok.loc, .extra = extra }, &.{});
1772 break :blk not_found;
1773 } else res: {
1774 var embed_args: []const TokenWithExpansionLocs = &.{};
1775 const include_str = (try pp.reconstructIncludeString(arg, &embed_args, arg[0])) orelse
1776 break :res not_found;
1777
1778 var prev = tokFromRaw(raw);
1779 prev.id = .eof;
1780 var it: struct {
1781 i: u32 = 0,
1782 slice: []const TokenWithExpansionLocs,
1783 prev: TokenWithExpansionLocs,
1784 fn next(it: *@This()) TokenWithExpansionLocs {
1785 while (it.i < it.slice.len) switch (it.slice[it.i].id) {
1786 .macro_ws, .whitespace => it.i += 1,
1787 else => break,
1788 } else return it.prev;
1789 defer it.i += 1;
1790 it.prev = it.slice[it.i];
1791 it.prev.id = .eof;
1792 return it.slice[it.i];
1793 }
1794 } = .{ .slice = embed_args, .prev = prev };
1795
1796 while (true) {
1797 const param_first = it.next();
1798 if (param_first.id == .eof) break;
1799 if (param_first.id != .identifier) {
1800 try pp.comp.addDiagnostic(
1801 .{ .tag = .malformed_embed_param, .loc = param_first.loc },
1802 param_first.expansionSlice(),
1803 );
1804 continue;
1805 }
1806
1807 const char_top = pp.char_buf.items.len;
1808 defer pp.char_buf.items.len = char_top;
1809
1810 const maybe_colon = it.next();
1811 const param = switch (maybe_colon.id) {
1812 .colon_colon => blk: {
1813 // vendor::param
1814 const param = it.next();
1815 if (param.id != .identifier) {
1816 try pp.comp.addDiagnostic(
1817 .{ .tag = .malformed_embed_param, .loc = param.loc },
1818 param.expansionSlice(),
1819 );
1820 continue;
1821 }
1822 const l_paren = it.next();
1823 if (l_paren.id != .l_paren) {
1824 try pp.comp.addDiagnostic(
1825 .{ .tag = .malformed_embed_param, .loc = l_paren.loc },
1826 l_paren.expansionSlice(),
1827 );
1828 continue;
1829 }
1830 break :blk "doesn't exist";
1831 },
1832 .l_paren => Attribute.normalize(pp.expandedSlice(param_first)),
1833 else => {
1834 try pp.comp.addDiagnostic(
1835 .{ .tag = .malformed_embed_param, .loc = maybe_colon.loc },
1836 maybe_colon.expansionSlice(),
1837 );
1838 continue;
1839 },
1840 };
1841
1842 var arg_count: u32 = 0;
1843 var first_arg: TokenWithExpansionLocs = undefined;
1844 while (true) {
1845 const next = it.next();
1846 if (next.id == .eof) {
1847 try pp.comp.addDiagnostic(
1848 .{ .tag = .malformed_embed_limit, .loc = param_first.loc },
1849 param_first.expansionSlice(),
1850 );
1851 break;
1852 }
1853 if (next.id == .r_paren) break;
1854 arg_count += 1;
1855 if (arg_count == 1) first_arg = next;
1856 }
1857
1858 if (std.mem.eql(u8, param, "limit")) {
1859 if (arg_count != 1) {
1860 try pp.comp.addDiagnostic(
1861 .{ .tag = .malformed_embed_limit, .loc = param_first.loc },
1862 param_first.expansionSlice(),
1863 );
1864 continue;
1865 }
1866 if (first_arg.id != .pp_num) {
1867 try pp.comp.addDiagnostic(
1868 .{ .tag = .malformed_embed_limit, .loc = param_first.loc },
1869 param_first.expansionSlice(),
1870 );
1871 continue;
1872 }
1873 _ = std.fmt.parseInt(u32, pp.expandedSlice(first_arg), 10) catch {
1874 break :res not_found;
1875 };
1876 } else if (!std.mem.eql(u8, param, "prefix") and !std.mem.eql(u8, param, "suffix") and
1877 !std.mem.eql(u8, param, "if_empty"))
1878 {
1879 break :res not_found;
1880 }
1881 }
1882
1883 const include_type: Compilation.IncludeType = switch (include_str[0]) {
1884 '"' => .quotes,
1885 '<' => .angle_brackets,
1886 else => unreachable,
1887 };
1888 const filename = include_str[1 .. include_str.len - 1];
1889 const contents = (try pp.comp.findEmbed(filename, arg[0].loc.id, include_type, 1)) orelse
1890 break :res not_found;
1891
1892 defer pp.comp.gpa.free(contents);
1893 break :res if (contents.len != 0) "1\n" else "2\n";
1894 };
1895 const start = pp.comp.generated_buf.items.len;
1896 try pp.comp.generated_buf.appendSlice(pp.comp.gpa, result);
1897 try buf.append(try pp.makeGeneratedToken(start, .pp_num, tokFromRaw(raw)));
1898 },
1899 .macro_param_pragma_operator => {
1900 const param_toks = expanded_args.items[0];
1901 // Clang and GCC require exactly one token (so, no parentheses or string pasting)
1902 // even though their error messages indicate otherwise. Ours is slightly more
1903 // descriptive.
1904 var invalid: ?TokenWithExpansionLocs = null;
1905 var string: ?TokenWithExpansionLocs = null;
1906 for (param_toks) |tok| switch (tok.id) {
1907 .string_literal => {
1908 if (string) |_| invalid = tok else string = tok;
1909 },
1910 .macro_ws => continue,
1911 .comment => continue,
1912 else => {
1913 invalid = tok;
1914 break;
1915 },
1916 };
1917 if (string == null and invalid == null) invalid = .{ .loc = macro_tok.loc, .id = .eof };
1918 if (invalid) |some| try pp.comp.addDiagnostic(
1919 .{ .tag = .pragma_operator_string_literal, .loc = some.loc },
1920 some.expansionSlice(),
1921 ) else try pp.pragmaOperator(string.?, macro_tok.loc);
1922 },
1923 .comma => {
1924 if (tok_i + 2 < func_macro.tokens.len and func_macro.tokens[tok_i + 1].id == .hash_hash) {
1925 const hash_hash = func_macro.tokens[tok_i + 1];
1926 var maybe_va_args = func_macro.tokens[tok_i + 2];
1927 var consumed: usize = 2;
1928 if (maybe_va_args.id == .macro_ws and tok_i + 3 < func_macro.tokens.len) {
1929 consumed = 3;
1930 maybe_va_args = func_macro.tokens[tok_i + 3];
1931 }
1932 if (maybe_va_args.id == .keyword_va_args) {
1933 // GNU extension: `, ##__VA_ARGS__` deletes the comma if __VA_ARGS__ is empty
1934 tok_i += consumed;
1935 if (func_macro.params.len == expanded_args.items.len) {
1936 // Empty __VA_ARGS__, drop the comma
1937 try pp.err(hash_hash, .comma_deletion_va_args);
1938 } else if (func_macro.params.len == 0 and expanded_args.items.len == 1 and expanded_args.items[0].len == 0) {
1939 // Ambiguous whether this is "empty __VA_ARGS__" or "__VA_ARGS__ omitted"
1940 if (pp.comp.langopts.standard.isGNU()) {
1941 // GNU standard, drop the comma
1942 try pp.err(hash_hash, .comma_deletion_va_args);
1943 } else {
1944 // C standard, retain the comma
1945 try buf.append(tokFromRaw(raw));
1946 }
1947 } else {
1948 try buf.append(tokFromRaw(raw));
1949 if (expanded_variable_arguments.items.len > 0 or variable_arguments.items.len == func_macro.params.len) {
1950 try pp.err(hash_hash, .comma_deletion_va_args);
1951 }
1952 const raw_loc = Source.Location{
1953 .id = maybe_va_args.source,
1954 .byte_offset = maybe_va_args.start,
1955 .line = maybe_va_args.line,
1956 };
1957 try bufCopyTokens(&buf, expanded_variable_arguments.items, &.{raw_loc});
1958 }
1959 continue;
1960 }
1961 }
1962 // Regular comma, no token pasting with __VA_ARGS__
1963 try buf.append(tokFromRaw(raw));
1964 },
1965 else => try buf.append(tokFromRaw(raw)),
1966 }
1967 }
1968 removePlacemarkers(&buf);
1969
1970 const macro_expansion_locs = macro_tok.expansionSlice();
1971 for (buf.items) |*tok| {
1972 try tok.addExpansionLocation(pp.gpa, &.{macro_tok.loc});
1973 try tok.addExpansionLocation(pp.gpa, macro_expansion_locs);
1974 const tok_hidelist = pp.hideset.get(tok.loc);
1975 const new_hidelist = try pp.hideset.@"union"(tok_hidelist, hideset);
1976 try pp.hideset.put(tok.loc, new_hidelist);
1977 }
1978
1979 return buf;
1980}
1981
1982fn expandVaOpt(
1983 pp: *Preprocessor,
1984 buf: *ExpandBuf,
1985 raw: RawToken,
1986 should_expand: bool,
1987) !void {
1988 if (!should_expand) return;
1989
1990 const source = pp.comp.getSource(raw.source);
1991 var tokenizer: Tokenizer = .{
1992 .buf = source.buf,
1993 .index = raw.start,
1994 .source = raw.source,
1995 .langopts = pp.comp.langopts,
1996 .line = raw.line,
1997 };
1998 while (tokenizer.index < raw.end) {
1999 const tok = tokenizer.next();
2000 try buf.append(tokFromRaw(tok));
2001 }
2002}
2003
2004fn bufCopyTokens(buf: *ExpandBuf, tokens: []const TokenWithExpansionLocs, src: []const Source.Location) !void {
2005 try buf.ensureUnusedCapacity(tokens.len);
2006 for (tokens) |tok| {
2007 var copy = try tok.dupe(buf.allocator);
2008 errdefer TokenWithExpansionLocs.free(copy.expansion_locs, buf.allocator);
2009 try copy.addExpansionLocation(buf.allocator, src);
2010 buf.appendAssumeCapacity(copy);
2011 }
2012}
2013
2014fn nextBufToken(
2015 pp: *Preprocessor,
2016 tokenizer: *Tokenizer,
2017 buf: *ExpandBuf,
2018 start_idx: *usize,
2019 end_idx: *usize,
2020 extend_buf: bool,
2021) Error!TokenWithExpansionLocs {
2022 start_idx.* += 1;
2023 if (start_idx.* == buf.items.len and start_idx.* >= end_idx.*) {
2024 if (extend_buf) {
2025 const raw_tok = tokenizer.next();
2026 if (raw_tok.id.isMacroIdentifier() and
2027 pp.poisoned_identifiers.get(pp.tokSlice(raw_tok)) != null)
2028 try pp.err(raw_tok, .poisoned_identifier);
2029
2030 if (raw_tok.id == .nl) pp.add_expansion_nl += 1;
2031
2032 const new_tok = tokFromRaw(raw_tok);
2033 end_idx.* += 1;
2034 try buf.append(new_tok);
2035 return new_tok;
2036 } else {
2037 return TokenWithExpansionLocs{ .id = .eof, .loc = .{ .id = .generated } };
2038 }
2039 } else {
2040 return buf.items[start_idx.*];
2041 }
2042}
2043
2044fn collectMacroFuncArguments(
2045 pp: *Preprocessor,
2046 tokenizer: *Tokenizer,
2047 buf: *ExpandBuf,
2048 start_idx: *usize,
2049 end_idx: *usize,
2050 extend_buf: bool,
2051 is_builtin: bool,
2052 r_paren: *TokenWithExpansionLocs,
2053) !MacroArguments {
2054 const name_tok = buf.items[start_idx.*];
2055 const saved_tokenizer = tokenizer.*;
2056 const old_end = end_idx.*;
2057
2058 while (true) {
2059 const tok = try nextBufToken(pp, tokenizer, buf, start_idx, end_idx, extend_buf);
2060 switch (tok.id) {
2061 .nl, .whitespace, .macro_ws => {},
2062 .l_paren => break,
2063 else => {
2064 if (is_builtin) {
2065 try pp.errStr(name_tok, .missing_lparen_after_builtin, pp.expandedSlice(name_tok));
2066 }
2067 // Not a macro function call, go over normal identifier, rewind
2068 tokenizer.* = saved_tokenizer;
2069 end_idx.* = old_end;
2070 return error.MissingLParen;
2071 },
2072 }
2073 }
2074
2075 // collect the arguments.
2076 var parens: u32 = 0;
2077 var args = MacroArguments.init(pp.gpa);
2078 errdefer deinitMacroArguments(pp.gpa, &args);
2079 var curArgument = std.ArrayList(TokenWithExpansionLocs).init(pp.gpa);
2080 defer curArgument.deinit();
2081 while (true) {
2082 var tok = try nextBufToken(pp, tokenizer, buf, start_idx, end_idx, extend_buf);
2083 tok.flags.is_macro_arg = true;
2084 switch (tok.id) {
2085 .comma => {
2086 if (parens == 0) {
2087 const owned = try curArgument.toOwnedSlice();
2088 errdefer pp.gpa.free(owned);
2089 try args.append(owned);
2090 } else {
2091 const duped = try tok.dupe(pp.gpa);
2092 errdefer TokenWithExpansionLocs.free(duped.expansion_locs, pp.gpa);
2093 try curArgument.append(duped);
2094 }
2095 },
2096 .l_paren => {
2097 const duped = try tok.dupe(pp.gpa);
2098 errdefer TokenWithExpansionLocs.free(duped.expansion_locs, pp.gpa);
2099 try curArgument.append(duped);
2100 parens += 1;
2101 },
2102 .r_paren => {
2103 if (parens == 0) {
2104 const owned = try curArgument.toOwnedSlice();
2105 errdefer pp.gpa.free(owned);
2106 try args.append(owned);
2107 r_paren.* = tok;
2108 break;
2109 } else {
2110 const duped = try tok.dupe(pp.gpa);
2111 errdefer TokenWithExpansionLocs.free(duped.expansion_locs, pp.gpa);
2112 try curArgument.append(duped);
2113 parens -= 1;
2114 }
2115 },
2116 .eof => {
2117 {
2118 const owned = try curArgument.toOwnedSlice();
2119 errdefer pp.gpa.free(owned);
2120 try args.append(owned);
2121 }
2122 tokenizer.* = saved_tokenizer;
2123 try pp.comp.addDiagnostic(
2124 .{ .tag = .unterminated_macro_arg_list, .loc = name_tok.loc },
2125 name_tok.expansionSlice(),
2126 );
2127 return error.Unterminated;
2128 },
2129 .nl, .whitespace => {
2130 try curArgument.append(.{ .id = .macro_ws, .loc = tok.loc });
2131 },
2132 else => {
2133 const duped = try tok.dupe(pp.gpa);
2134 errdefer TokenWithExpansionLocs.free(duped.expansion_locs, pp.gpa);
2135 try curArgument.append(duped);
2136 },
2137 }
2138 }
2139
2140 return args;
2141}
2142
2143fn removeExpandedTokens(pp: *Preprocessor, buf: *ExpandBuf, start: usize, len: usize, moving_end_idx: *usize) !void {
2144 for (buf.items[start .. start + len]) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2145 try buf.replaceRange(start, len, &.{});
2146 moving_end_idx.* -|= len;
2147}
2148
2149/// The behavior of `defined` depends on whether we are in a preprocessor
2150/// expression context (#if or #elif) or not.
2151/// In a non-expression context it's just an identifier. Within a preprocessor
2152/// expression it is a unary operator or one-argument function.
2153const EvalContext = enum {
2154 expr,
2155 non_expr,
2156};
2157
2158/// Helper for safely iterating over a slice of tokens while skipping whitespace
2159const TokenIterator = struct {
2160 toks: []const TokenWithExpansionLocs,
2161 i: usize,
2162
2163 fn init(toks: []const TokenWithExpansionLocs) TokenIterator {
2164 return .{ .toks = toks, .i = 0 };
2165 }
2166
2167 fn nextNoWS(self: *TokenIterator) ?TokenWithExpansionLocs {
2168 while (self.i < self.toks.len) : (self.i += 1) {
2169 const tok = self.toks[self.i];
2170 if (tok.id == .whitespace or tok.id == .macro_ws) continue;
2171
2172 self.i += 1;
2173 return tok;
2174 }
2175 return null;
2176 }
2177};
2178
2179fn expandMacroExhaustive(
2180 pp: *Preprocessor,
2181 tokenizer: *Tokenizer,
2182 buf: *ExpandBuf,
2183 start_idx: usize,
2184 end_idx: usize,
2185 extend_buf: bool,
2186 eval_ctx: EvalContext,
2187) MacroError!void {
2188 var moving_end_idx = end_idx;
2189 var advance_index: usize = 0;
2190 // rescan loop
2191 var do_rescan = true;
2192 while (do_rescan) {
2193 do_rescan = false;
2194 // expansion loop
2195 var idx: usize = start_idx + advance_index;
2196 while (idx < moving_end_idx) {
2197 const macro_tok = buf.items[idx];
2198 if (macro_tok.id == .keyword_defined and eval_ctx == .expr) {
2199 idx += 1;
2200 var it = TokenIterator.init(buf.items[idx..moving_end_idx]);
2201 if (it.nextNoWS()) |tok| {
2202 switch (tok.id) {
2203 .l_paren => {
2204 _ = it.nextNoWS(); // eat (what should be) identifier
2205 _ = it.nextNoWS(); // eat (what should be) r paren
2206 },
2207 .identifier, .extended_identifier => {},
2208 else => {},
2209 }
2210 }
2211 idx += it.i;
2212 continue;
2213 }
2214 if (!macro_tok.id.isMacroIdentifier() or macro_tok.flags.expansion_disabled) {
2215 idx += 1;
2216 continue;
2217 }
2218 const expanded = pp.expandedSlice(macro_tok);
2219 const macro = pp.defines.getPtr(expanded) orelse {
2220 idx += 1;
2221 continue;
2222 };
2223 const macro_hidelist = pp.hideset.get(macro_tok.loc);
2224 if (pp.hideset.contains(macro_hidelist, expanded)) {
2225 idx += 1;
2226 continue;
2227 }
2228
2229 macro_handler: {
2230 if (macro.is_func) {
2231 var r_paren: TokenWithExpansionLocs = undefined;
2232 var macro_scan_idx = idx;
2233 // to be saved in case this doesn't turn out to be a call
2234 const args = pp.collectMacroFuncArguments(
2235 tokenizer,
2236 buf,
2237 &macro_scan_idx,
2238 &moving_end_idx,
2239 extend_buf,
2240 macro.is_builtin,
2241 &r_paren,
2242 ) catch |er| switch (er) {
2243 error.MissingLParen => {
2244 if (!buf.items[idx].flags.is_macro_arg) buf.items[idx].flags.expansion_disabled = true;
2245 idx += 1;
2246 break :macro_handler;
2247 },
2248 error.Unterminated => {
2249 if (pp.comp.langopts.emulate == .gcc) idx += 1;
2250 try pp.removeExpandedTokens(buf, idx, macro_scan_idx - idx, &moving_end_idx);
2251 break :macro_handler;
2252 },
2253 else => |e| return e,
2254 };
2255 assert(r_paren.id == .r_paren);
2256 var free_arg_expansion_locs = false;
2257 defer {
2258 for (args.items) |item| {
2259 if (free_arg_expansion_locs) for (item) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2260 pp.gpa.free(item);
2261 }
2262 args.deinit();
2263 }
2264 const r_paren_hidelist = pp.hideset.get(r_paren.loc);
2265 var hs = try pp.hideset.intersection(macro_hidelist, r_paren_hidelist);
2266 hs = try pp.hideset.prepend(macro_tok.loc, hs);
2267
2268 var args_count: u32 = @intCast(args.items.len);
2269 // if the macro has zero arguments g() args_count is still 1
2270 // an empty token list g() and a whitespace-only token list g( )
2271 // counts as zero arguments for the purposes of argument-count validation
2272 if (args_count == 1 and macro.params.len == 0) {
2273 for (args.items[0]) |tok| {
2274 if (tok.id != .macro_ws) break;
2275 } else {
2276 args_count = 0;
2277 }
2278 }
2279
2280 // Validate argument count.
2281 const extra = Diagnostics.Message.Extra{
2282 .arguments = .{ .expected = @intCast(macro.params.len), .actual = args_count },
2283 };
2284 if (macro.var_args and args_count < macro.params.len) {
2285 free_arg_expansion_locs = true;
2286 try pp.comp.addDiagnostic(
2287 .{ .tag = .expected_at_least_arguments, .loc = buf.items[idx].loc, .extra = extra },
2288 buf.items[idx].expansionSlice(),
2289 );
2290 idx += 1;
2291 try pp.removeExpandedTokens(buf, idx, macro_scan_idx - idx + 1, &moving_end_idx);
2292 continue;
2293 }
2294 if (!macro.var_args and args_count != macro.params.len) {
2295 free_arg_expansion_locs = true;
2296 try pp.comp.addDiagnostic(
2297 .{ .tag = .expected_arguments, .loc = buf.items[idx].loc, .extra = extra },
2298 buf.items[idx].expansionSlice(),
2299 );
2300 idx += 1;
2301 try pp.removeExpandedTokens(buf, idx, macro_scan_idx - idx + 1, &moving_end_idx);
2302 continue;
2303 }
2304 var expanded_args = MacroArguments.init(pp.gpa);
2305 defer deinitMacroArguments(pp.gpa, &expanded_args);
2306 try expanded_args.ensureTotalCapacity(args.items.len);
2307 for (args.items) |arg| {
2308 var expand_buf = ExpandBuf.init(pp.gpa);
2309 errdefer expand_buf.deinit();
2310 try expand_buf.appendSlice(arg);
2311
2312 try pp.expandMacroExhaustive(tokenizer, &expand_buf, 0, expand_buf.items.len, false, eval_ctx);
2313
2314 expanded_args.appendAssumeCapacity(try expand_buf.toOwnedSlice());
2315 }
2316
2317 var res = try pp.expandFuncMacro(macro_tok, macro, &args, &expanded_args, hs);
2318 defer res.deinit();
2319 const tokens_added = res.items.len;
2320 const tokens_removed = macro_scan_idx - idx + 1;
2321 for (buf.items[idx .. idx + tokens_removed]) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2322 try buf.replaceRange(idx, tokens_removed, res.items);
2323
2324 moving_end_idx += tokens_added;
2325 // Overflow here means that we encountered an unterminated argument list
2326 // while expanding the body of this macro.
2327 moving_end_idx -|= tokens_removed;
2328 idx += tokens_added;
2329 do_rescan = true;
2330 } else {
2331 const res = try pp.expandObjMacro(macro);
2332 defer res.deinit();
2333
2334 const hs = try pp.hideset.prepend(macro_tok.loc, macro_hidelist);
2335
2336 const macro_expansion_locs = macro_tok.expansionSlice();
2337 var increment_idx_by = res.items.len;
2338 for (res.items, 0..) |*tok, i| {
2339 tok.flags.is_macro_arg = macro_tok.flags.is_macro_arg;
2340 try tok.addExpansionLocation(pp.gpa, &.{macro_tok.loc});
2341 try tok.addExpansionLocation(pp.gpa, macro_expansion_locs);
2342
2343 const tok_hidelist = pp.hideset.get(tok.loc);
2344 const new_hidelist = try pp.hideset.@"union"(tok_hidelist, hs);
2345 try pp.hideset.put(tok.loc, new_hidelist);
2346
2347 if (tok.id == .keyword_defined and eval_ctx == .expr) {
2348 try pp.comp.addDiagnostic(.{
2349 .tag = .expansion_to_defined,
2350 .loc = tok.loc,
2351 }, tok.expansionSlice());
2352 }
2353
2354 if (i < increment_idx_by and (tok.id == .keyword_defined or pp.defines.contains(pp.expandedSlice(tok.*)))) {
2355 increment_idx_by = i;
2356 }
2357 }
2358
2359 TokenWithExpansionLocs.free(buf.items[idx].expansion_locs, pp.gpa);
2360 try buf.replaceRange(idx, 1, res.items);
2361 idx += increment_idx_by;
2362 moving_end_idx = moving_end_idx + res.items.len - 1;
2363 do_rescan = true;
2364 }
2365 }
2366 if (idx - start_idx == advance_index + 1 and !do_rescan) {
2367 advance_index += 1;
2368 }
2369 } // end of replacement phase
2370 }
2371 // end of scanning phase
2372
2373 // trim excess buffer
2374 for (buf.items[moving_end_idx..]) |item| {
2375 TokenWithExpansionLocs.free(item.expansion_locs, pp.gpa);
2376 }
2377 buf.items.len = moving_end_idx;
2378}
2379
2380/// Try to expand a macro after a possible candidate has been read from the `tokenizer`
2381/// into the `raw` token passed as argument
2382fn expandMacro(pp: *Preprocessor, tokenizer: *Tokenizer, raw: RawToken) MacroError!void {
2383 var source_tok = tokFromRaw(raw);
2384 if (!raw.id.isMacroIdentifier()) {
2385 source_tok.id.simplifyMacroKeyword();
2386 return pp.addToken(source_tok);
2387 }
2388 pp.top_expansion_buf.items.len = 0;
2389 try pp.top_expansion_buf.append(source_tok);
2390 pp.expansion_source_loc = source_tok.loc;
2391
2392 pp.hideset.clearRetainingCapacity();
2393 try pp.expandMacroExhaustive(tokenizer, &pp.top_expansion_buf, 0, 1, true, .non_expr);
2394 try pp.ensureUnusedTokenCapacity(pp.top_expansion_buf.items.len);
2395 for (pp.top_expansion_buf.items) |*tok| {
2396 if (tok.id == .macro_ws and !pp.preserve_whitespace) {
2397 TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2398 continue;
2399 }
2400 if (tok.id == .comment and !pp.comp.langopts.preserve_comments_in_macros) {
2401 TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2402 continue;
2403 }
2404 if (tok.id == .placemarker) {
2405 TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2406 continue;
2407 }
2408 tok.id.simplifyMacroKeywordExtra(true);
2409 pp.addTokenAssumeCapacity(tok.*);
2410 }
2411 if (pp.preserve_whitespace) {
2412 try pp.ensureUnusedTokenCapacity(pp.add_expansion_nl);
2413 while (pp.add_expansion_nl > 0) : (pp.add_expansion_nl -= 1) {
2414 pp.addTokenAssumeCapacity(.{ .id = .nl, .loc = .{
2415 .id = tokenizer.source,
2416 .line = tokenizer.line,
2417 } });
2418 }
2419 }
2420}
2421
2422fn expandedSliceExtra(pp: *const Preprocessor, tok: anytype, macro_ws_handling: enum { single_macro_ws, preserve_macro_ws }) []const u8 {
2423 if (tok.id.lexeme()) |some| {
2424 if (!tok.id.allowsDigraphs(pp.comp.langopts) and !(tok.id == .macro_ws and macro_ws_handling == .preserve_macro_ws)) return some;
2425 }
2426 var tmp_tokenizer = Tokenizer{
2427 .buf = pp.comp.getSource(tok.loc.id).buf,
2428 .langopts = pp.comp.langopts,
2429 .index = tok.loc.byte_offset,
2430 .source = .generated,
2431 };
2432 if (tok.id == .macro_string) {
2433 while (true) : (tmp_tokenizer.index += 1) {
2434 if (tmp_tokenizer.buf[tmp_tokenizer.index] == '>') break;
2435 }
2436 return tmp_tokenizer.buf[tok.loc.byte_offset .. tmp_tokenizer.index + 1];
2437 }
2438 const res = tmp_tokenizer.next();
2439 return tmp_tokenizer.buf[res.start..res.end];
2440}
2441
2442/// Get expanded token source string.
2443pub fn expandedSlice(pp: *const Preprocessor, tok: anytype) []const u8 {
2444 return pp.expandedSliceExtra(tok, .single_macro_ws);
2445}
2446
2447/// Concat two tokens and add the result to pp.generated
2448fn pasteTokens(pp: *Preprocessor, lhs_toks: *ExpandBuf, rhs_toks: []const TokenWithExpansionLocs) Error!void {
2449 const lhs = while (lhs_toks.popOrNull()) |lhs| {
2450 if ((pp.comp.langopts.preserve_comments_in_macros and lhs.id == .comment) or
2451 (lhs.id != .macro_ws and lhs.id != .comment))
2452 break lhs;
2453
2454 TokenWithExpansionLocs.free(lhs.expansion_locs, pp.gpa);
2455 } else {
2456 return bufCopyTokens(lhs_toks, rhs_toks, &.{});
2457 };
2458
2459 var rhs_rest: u32 = 1;
2460 const rhs = for (rhs_toks) |rhs| {
2461 if ((pp.comp.langopts.preserve_comments_in_macros and rhs.id == .comment) or
2462 (rhs.id != .macro_ws and rhs.id != .comment))
2463 break rhs;
2464
2465 rhs_rest += 1;
2466 } else {
2467 return lhs_toks.appendAssumeCapacity(lhs);
2468 };
2469 defer TokenWithExpansionLocs.free(lhs.expansion_locs, pp.gpa);
2470
2471 const start = pp.comp.generated_buf.items.len;
2472 const end = start + pp.expandedSlice(lhs).len + pp.expandedSlice(rhs).len;
2473 try pp.comp.generated_buf.ensureTotalCapacity(pp.gpa, end + 1); // +1 for a newline
2474 // We cannot use the same slices here since they might be invalidated by `ensureCapacity`
2475 pp.comp.generated_buf.appendSliceAssumeCapacity(pp.expandedSlice(lhs));
2476 pp.comp.generated_buf.appendSliceAssumeCapacity(pp.expandedSlice(rhs));
2477 pp.comp.generated_buf.appendAssumeCapacity('\n');
2478
2479 // Try to tokenize the result.
2480 var tmp_tokenizer = Tokenizer{
2481 .buf = pp.comp.generated_buf.items,
2482 .langopts = pp.comp.langopts,
2483 .index = @intCast(start),
2484 .source = .generated,
2485 };
2486 const pasted_token = tmp_tokenizer.nextNoWSComments();
2487 const next = tmp_tokenizer.nextNoWSComments();
2488 const pasted_id = if (lhs.id == .placemarker and rhs.id == .placemarker)
2489 .placemarker
2490 else
2491 pasted_token.id;
2492 try lhs_toks.append(try pp.makeGeneratedToken(start, pasted_id, lhs));
2493
2494 if (next.id != .nl and next.id != .eof) {
2495 try pp.errStr(
2496 lhs,
2497 .pasting_formed_invalid,
2498 try pp.comp.diagnostics.arena.allocator().dupe(u8, pp.comp.generated_buf.items[start..end]),
2499 );
2500 try lhs_toks.append(tokFromRaw(next));
2501 }
2502
2503 try bufCopyTokens(lhs_toks, rhs_toks[rhs_rest..], &.{});
2504}
2505
2506fn makeGeneratedToken(pp: *Preprocessor, start: usize, id: Token.Id, source: TokenWithExpansionLocs) !TokenWithExpansionLocs {
2507 var pasted_token = TokenWithExpansionLocs{ .id = id, .loc = .{
2508 .id = .generated,
2509 .byte_offset = @intCast(start),
2510 .line = pp.generated_line,
2511 } };
2512 pp.generated_line += 1;
2513 try pasted_token.addExpansionLocation(pp.gpa, &.{source.loc});
2514 try pasted_token.addExpansionLocation(pp.gpa, source.expansionSlice());
2515 return pasted_token;
2516}
2517
2518/// Defines a new macro and warns if it is a duplicate
2519fn defineMacro(pp: *Preprocessor, define_tok: RawToken, name_tok: RawToken, macro: Macro) Error!void {
2520 const name_str = pp.tokSlice(name_tok);
2521 const gop = try pp.defines.getOrPut(pp.gpa, name_str);
2522 if (gop.found_existing and !gop.value_ptr.eql(macro, pp)) {
2523 const tag: Diagnostics.Tag = if (gop.value_ptr.is_builtin) .builtin_macro_redefined else .macro_redefined;
2524 const start = pp.comp.diagnostics.list.items.len;
2525 try pp.comp.addDiagnostic(.{
2526 .tag = tag,
2527 .loc = .{ .id = name_tok.source, .byte_offset = name_tok.start, .line = name_tok.line },
2528 .extra = .{ .str = name_str },
2529 }, &.{});
2530 if (!gop.value_ptr.is_builtin and pp.comp.diagnostics.list.items.len != start) {
2531 try pp.comp.addDiagnostic(.{
2532 .tag = .previous_definition,
2533 .loc = gop.value_ptr.loc,
2534 }, &.{});
2535 }
2536 }
2537 if (pp.verbose) {
2538 pp.verboseLog(name_tok, "macro {s} defined", .{name_str});
2539 }
2540 if (pp.store_macro_tokens) {
2541 try pp.addToken(tokFromRaw(define_tok));
2542 }
2543 gop.value_ptr.* = macro;
2544}
2545
2546/// Handle a #define directive.
2547fn define(pp: *Preprocessor, tokenizer: *Tokenizer, define_tok: RawToken) Error!void {
2548 // Get macro name and validate it.
2549 const macro_name = tokenizer.nextNoWS();
2550 if (macro_name.id == .keyword_defined) {
2551 try pp.err(macro_name, .defined_as_macro_name);
2552 return skipToNl(tokenizer);
2553 }
2554 if (!macro_name.id.isMacroIdentifier()) {
2555 try pp.err(macro_name, .macro_name_must_be_identifier);
2556 return skipToNl(tokenizer);
2557 }
2558 var macro_name_token_id = macro_name.id;
2559 macro_name_token_id.simplifyMacroKeyword();
2560 switch (macro_name_token_id) {
2561 .identifier, .extended_identifier => {},
2562 else => if (macro_name_token_id.isMacroIdentifier()) {
2563 try pp.err(macro_name, .keyword_macro);
2564 },
2565 }
2566
2567 // Check for function macros and empty defines.
2568 var first = tokenizer.next();
2569 switch (first.id) {
2570 .nl, .eof => return pp.defineMacro(define_tok, macro_name, .{
2571 .params = &.{},
2572 .tokens = &.{},
2573 .var_args = false,
2574 .loc = tokFromRaw(macro_name).loc,
2575 .is_func = false,
2576 }),
2577 .whitespace => first = tokenizer.next(),
2578 .l_paren => return pp.defineFn(tokenizer, define_tok, macro_name, first),
2579 else => try pp.err(first, .whitespace_after_macro_name),
2580 }
2581 if (first.id == .hash_hash) {
2582 try pp.err(first, .hash_hash_at_start);
2583 return skipToNl(tokenizer);
2584 }
2585 first.id.simplifyMacroKeyword();
2586
2587 pp.token_buf.items.len = 0; // Safe to use since we can only be in one directive at a time.
2588
2589 var need_ws = false;
2590 // Collect the token body and validate any ## found.
2591 var tok = first;
2592 while (true) {
2593 tok.id.simplifyMacroKeyword();
2594 switch (tok.id) {
2595 .hash_hash => {
2596 const next = tokenizer.nextNoWSComments();
2597 switch (next.id) {
2598 .nl, .eof => {
2599 try pp.err(tok, .hash_hash_at_end);
2600 return;
2601 },
2602 .hash_hash => {
2603 try pp.err(next, .hash_hash_at_end);
2604 return;
2605 },
2606 else => {},
2607 }
2608 try pp.token_buf.append(tok);
2609 try pp.token_buf.append(next);
2610 },
2611 .nl, .eof => break,
2612 .comment => if (pp.comp.langopts.preserve_comments_in_macros) {
2613 if (need_ws) {
2614 need_ws = false;
2615 try pp.token_buf.append(.{ .id = .macro_ws, .source = .generated });
2616 }
2617 try pp.token_buf.append(tok);
2618 },
2619 .whitespace => need_ws = true,
2620 .unterminated_string_literal, .unterminated_char_literal, .empty_char_literal => |tag| {
2621 try pp.err(tok, invalidTokenDiagnostic(tag));
2622 try pp.token_buf.append(tok);
2623 },
2624 .unterminated_comment => try pp.err(tok, .unterminated_comment),
2625 else => {
2626 if (tok.id != .whitespace and need_ws) {
2627 need_ws = false;
2628 try pp.token_buf.append(.{ .id = .macro_ws, .source = .generated });
2629 }
2630 try pp.token_buf.append(tok);
2631 },
2632 }
2633 tok = tokenizer.next();
2634 }
2635
2636 const list = try pp.arena.allocator().dupe(RawToken, pp.token_buf.items);
2637 try pp.defineMacro(define_tok, macro_name, .{
2638 .loc = tokFromRaw(macro_name).loc,
2639 .tokens = list,
2640 .params = undefined,
2641 .is_func = false,
2642 .var_args = false,
2643 });
2644}
2645
2646/// Handle a function like #define directive.
2647fn defineFn(pp: *Preprocessor, tokenizer: *Tokenizer, define_tok: RawToken, macro_name: RawToken, l_paren: RawToken) Error!void {
2648 assert(macro_name.id.isMacroIdentifier());
2649 var params = std.ArrayList([]const u8).init(pp.gpa);
2650 defer params.deinit();
2651
2652 // Parse the parameter list.
2653 var gnu_var_args: []const u8 = "";
2654 var var_args = false;
2655 while (true) {
2656 var tok = tokenizer.nextNoWS();
2657 if (tok.id == .r_paren) break;
2658 if (tok.id == .eof) return pp.err(tok, .unterminated_macro_param_list);
2659 if (tok.id == .ellipsis) {
2660 var_args = true;
2661 const r_paren = tokenizer.nextNoWS();
2662 if (r_paren.id != .r_paren) {
2663 try pp.err(r_paren, .missing_paren_param_list);
2664 try pp.err(l_paren, .to_match_paren);
2665 return skipToNl(tokenizer);
2666 }
2667 break;
2668 }
2669 if (!tok.id.isMacroIdentifier()) {
2670 try pp.err(tok, .invalid_token_param_list);
2671 return skipToNl(tokenizer);
2672 }
2673
2674 try params.append(pp.tokSlice(tok));
2675
2676 tok = tokenizer.nextNoWS();
2677 if (tok.id == .ellipsis) {
2678 try pp.err(tok, .gnu_va_macro);
2679 gnu_var_args = params.pop();
2680 const r_paren = tokenizer.nextNoWS();
2681 if (r_paren.id != .r_paren) {
2682 try pp.err(r_paren, .missing_paren_param_list);
2683 try pp.err(l_paren, .to_match_paren);
2684 return skipToNl(tokenizer);
2685 }
2686 break;
2687 } else if (tok.id == .r_paren) {
2688 break;
2689 } else if (tok.id != .comma) {
2690 try pp.err(tok, .expected_comma_param_list);
2691 return skipToNl(tokenizer);
2692 }
2693 }
2694
2695 var need_ws = false;
2696 // Collect the body tokens and validate # and ##'s found.
2697 pp.token_buf.items.len = 0; // Safe to use since we can only be in one directive at a time.
2698 tok_loop: while (true) {
2699 var tok = tokenizer.next();
2700 switch (tok.id) {
2701 .nl, .eof => break,
2702 .whitespace => need_ws = pp.token_buf.items.len != 0,
2703 .comment => if (!pp.comp.langopts.preserve_comments_in_macros) continue else {
2704 if (need_ws) {
2705 need_ws = false;
2706 try pp.token_buf.append(.{ .id = .macro_ws, .source = .generated });
2707 }
2708 try pp.token_buf.append(tok);
2709 },
2710 .hash => {
2711 if (tok.id != .whitespace and need_ws) {
2712 need_ws = false;
2713 try pp.token_buf.append(.{ .id = .macro_ws, .source = .generated });
2714 }
2715 const param = tokenizer.nextNoWS();
2716 blk: {
2717 if (var_args and param.id == .keyword_va_args) {
2718 tok.id = .stringify_va_args;
2719 try pp.token_buf.append(tok);
2720 continue :tok_loop;
2721 }
2722 if (!param.id.isMacroIdentifier()) break :blk;
2723 const s = pp.tokSlice(param);
2724 if (mem.eql(u8, s, gnu_var_args)) {
2725 tok.id = .stringify_va_args;
2726 try pp.token_buf.append(tok);
2727 continue :tok_loop;
2728 }
2729 for (params.items, 0..) |p, i| {
2730 if (mem.eql(u8, p, s)) {
2731 tok.id = .stringify_param;
2732 tok.end = @intCast(i);
2733 try pp.token_buf.append(tok);
2734 continue :tok_loop;
2735 }
2736 }
2737 }
2738 try pp.err(param, .hash_not_followed_param);
2739 return skipToNl(tokenizer);
2740 },
2741 .hash_hash => {
2742 need_ws = false;
2743 // if ## appears at the beginning, the token buf is still empty
2744 // in this case, error out
2745 if (pp.token_buf.items.len == 0) {
2746 try pp.err(tok, .hash_hash_at_start);
2747 return skipToNl(tokenizer);
2748 }
2749 const saved_tokenizer = tokenizer.*;
2750 const next = tokenizer.nextNoWSComments();
2751 if (next.id == .nl or next.id == .eof) {
2752 try pp.err(tok, .hash_hash_at_end);
2753 return;
2754 }
2755 tokenizer.* = saved_tokenizer;
2756 // convert the previous token to .macro_param_no_expand if it was .macro_param
2757 if (pp.token_buf.items[pp.token_buf.items.len - 1].id == .macro_param) {
2758 pp.token_buf.items[pp.token_buf.items.len - 1].id = .macro_param_no_expand;
2759 }
2760 try pp.token_buf.append(tok);
2761 },
2762 .unterminated_string_literal, .unterminated_char_literal, .empty_char_literal => |tag| {
2763 try pp.err(tok, invalidTokenDiagnostic(tag));
2764 try pp.token_buf.append(tok);
2765 },
2766 .unterminated_comment => try pp.err(tok, .unterminated_comment),
2767 else => {
2768 if (tok.id != .whitespace and need_ws) {
2769 need_ws = false;
2770 try pp.token_buf.append(.{ .id = .macro_ws, .source = .generated });
2771 }
2772 if (var_args and tok.id == .keyword_va_args) {
2773 // do nothing
2774 } else if (var_args and tok.id == .keyword_va_opt) {
2775 const opt_l_paren = tokenizer.next();
2776 if (opt_l_paren.id != .l_paren) {
2777 try pp.err(opt_l_paren, .va_opt_lparen);
2778 return skipToNl(tokenizer);
2779 }
2780 tok.start = opt_l_paren.end;
2781
2782 var parens: u32 = 0;
2783 while (true) {
2784 const opt_tok = tokenizer.next();
2785 switch (opt_tok.id) {
2786 .l_paren => parens += 1,
2787 .r_paren => if (parens == 0) {
2788 break;
2789 } else {
2790 parens -= 1;
2791 },
2792 .nl, .eof => {
2793 try pp.err(opt_tok, .va_opt_rparen);
2794 try pp.err(opt_l_paren, .to_match_paren);
2795 return skipToNl(tokenizer);
2796 },
2797 .whitespace => {},
2798 else => tok.end = opt_tok.end,
2799 }
2800 }
2801 } else if (tok.id.isMacroIdentifier()) {
2802 tok.id.simplifyMacroKeyword();
2803 const s = pp.tokSlice(tok);
2804 if (mem.eql(u8, gnu_var_args, s)) {
2805 tok.id = .keyword_va_args;
2806 } else for (params.items, 0..) |param, i| {
2807 if (mem.eql(u8, param, s)) {
2808 // NOTE: it doesn't matter to assign .macro_param_no_expand
2809 // here in case a ## was the previous token, because
2810 // ## processing will eat this token with the same semantics
2811 tok.id = .macro_param;
2812 tok.end = @intCast(i);
2813 break;
2814 }
2815 }
2816 }
2817 try pp.token_buf.append(tok);
2818 },
2819 }
2820 }
2821
2822 const param_list = try pp.arena.allocator().dupe([]const u8, params.items);
2823 const token_list = try pp.arena.allocator().dupe(RawToken, pp.token_buf.items);
2824 try pp.defineMacro(define_tok, macro_name, .{
2825 .is_func = true,
2826 .params = param_list,
2827 .var_args = var_args or gnu_var_args.len != 0,
2828 .tokens = token_list,
2829 .loc = tokFromRaw(macro_name).loc,
2830 });
2831}
2832
2833/// Handle an #embed directive
2834/// embedDirective : ("FILENAME" | <FILENAME>) embedParam*
2835/// embedParam : IDENTIFIER (:: IDENTIFIER)? '(' <tokens> ')'
2836fn embed(pp: *Preprocessor, tokenizer: *Tokenizer) MacroError!void {
2837 const first = tokenizer.nextNoWS();
2838 const filename_tok = pp.findIncludeFilenameToken(first, tokenizer, .ignore_trailing_tokens) catch |er| switch (er) {
2839 error.InvalidInclude => return,
2840 else => |e| return e,
2841 };
2842 defer TokenWithExpansionLocs.free(filename_tok.expansion_locs, pp.gpa);
2843
2844 // Check for empty filename.
2845 const tok_slice = pp.expandedSliceExtra(filename_tok, .single_macro_ws);
2846 if (tok_slice.len < 3) {
2847 try pp.err(first, .empty_filename);
2848 return;
2849 }
2850 const filename = tok_slice[1 .. tok_slice.len - 1];
2851 const include_type: Compilation.IncludeType = switch (filename_tok.id) {
2852 .string_literal => .quotes,
2853 .macro_string => .angle_brackets,
2854 else => unreachable,
2855 };
2856
2857 // Index into `token_buf`
2858 const Range = struct {
2859 start: u32,
2860 end: u32,
2861
2862 fn expand(opt_range: ?@This(), pp_: *Preprocessor, tokenizer_: *Tokenizer) !void {
2863 const range = opt_range orelse return;
2864 const slice = pp_.token_buf.items[range.start..range.end];
2865 for (slice) |tok| {
2866 try pp_.expandMacro(tokenizer_, tok);
2867 }
2868 }
2869 };
2870 pp.token_buf.items.len = 0;
2871
2872 var limit: ?u32 = null;
2873 var prefix: ?Range = null;
2874 var suffix: ?Range = null;
2875 var if_empty: ?Range = null;
2876 while (true) {
2877 const param_first = tokenizer.nextNoWS();
2878 switch (param_first.id) {
2879 .nl, .eof => break,
2880 .identifier => {},
2881 else => {
2882 try pp.err(param_first, .malformed_embed_param);
2883 continue;
2884 },
2885 }
2886
2887 const char_top = pp.char_buf.items.len;
2888 defer pp.char_buf.items.len = char_top;
2889
2890 const maybe_colon = tokenizer.colonColon();
2891 const param = switch (maybe_colon.id) {
2892 .colon_colon => blk: {
2893 // vendor::param
2894 const param = tokenizer.nextNoWS();
2895 if (param.id != .identifier) {
2896 try pp.err(param, .malformed_embed_param);
2897 continue;
2898 }
2899 const l_paren = tokenizer.nextNoWS();
2900 if (l_paren.id != .l_paren) {
2901 try pp.err(l_paren, .malformed_embed_param);
2902 continue;
2903 }
2904 try pp.char_buf.appendSlice(Attribute.normalize(pp.tokSlice(param_first)));
2905 try pp.char_buf.appendSlice("::");
2906 try pp.char_buf.appendSlice(Attribute.normalize(pp.tokSlice(param)));
2907 break :blk pp.char_buf.items;
2908 },
2909 .l_paren => Attribute.normalize(pp.tokSlice(param_first)),
2910 else => {
2911 try pp.err(maybe_colon, .malformed_embed_param);
2912 continue;
2913 },
2914 };
2915
2916 const start: u32 = @intCast(pp.token_buf.items.len);
2917 while (true) {
2918 const next = tokenizer.nextNoWS();
2919 if (next.id == .r_paren) break;
2920 if (next.id == .eof) {
2921 try pp.err(maybe_colon, .malformed_embed_param);
2922 break;
2923 }
2924 try pp.token_buf.append(next);
2925 }
2926 const end: u32 = @intCast(pp.token_buf.items.len);
2927
2928 if (std.mem.eql(u8, param, "limit")) {
2929 if (limit != null) {
2930 try pp.errStr(tokFromRaw(param_first), .duplicate_embed_param, "limit");
2931 continue;
2932 }
2933 if (start + 1 != end) {
2934 try pp.err(param_first, .malformed_embed_limit);
2935 continue;
2936 }
2937 const limit_tok = pp.token_buf.items[start];
2938 if (limit_tok.id != .pp_num) {
2939 try pp.err(param_first, .malformed_embed_limit);
2940 continue;
2941 }
2942 limit = std.fmt.parseInt(u32, pp.tokSlice(limit_tok), 10) catch {
2943 try pp.err(limit_tok, .malformed_embed_limit);
2944 continue;
2945 };
2946 pp.token_buf.items.len = start;
2947 } else if (std.mem.eql(u8, param, "prefix")) {
2948 if (prefix != null) {
2949 try pp.errStr(tokFromRaw(param_first), .duplicate_embed_param, "prefix");
2950 continue;
2951 }
2952 prefix = .{ .start = start, .end = end };
2953 } else if (std.mem.eql(u8, param, "suffix")) {
2954 if (suffix != null) {
2955 try pp.errStr(tokFromRaw(param_first), .duplicate_embed_param, "suffix");
2956 continue;
2957 }
2958 suffix = .{ .start = start, .end = end };
2959 } else if (std.mem.eql(u8, param, "if_empty")) {
2960 if (if_empty != null) {
2961 try pp.errStr(tokFromRaw(param_first), .duplicate_embed_param, "if_empty");
2962 continue;
2963 }
2964 if_empty = .{ .start = start, .end = end };
2965 } else {
2966 try pp.errStr(
2967 tokFromRaw(param_first),
2968 .unsupported_embed_param,
2969 try pp.comp.diagnostics.arena.allocator().dupe(u8, param),
2970 );
2971 pp.token_buf.items.len = start;
2972 }
2973 }
2974
2975 const embed_bytes = (try pp.comp.findEmbed(filename, first.source, include_type, limit)) orelse
2976 return pp.fatalNotFound(filename_tok, filename);
2977 defer pp.comp.gpa.free(embed_bytes);
2978
2979 try Range.expand(prefix, pp, tokenizer);
2980
2981 if (embed_bytes.len == 0) {
2982 try Range.expand(if_empty, pp, tokenizer);
2983 try Range.expand(suffix, pp, tokenizer);
2984 return;
2985 }
2986
2987 try pp.ensureUnusedTokenCapacity(2 * embed_bytes.len - 1); // N bytes and N-1 commas
2988
2989 // TODO: We currently only support systems with CHAR_BIT == 8
2990 // If the target's CHAR_BIT is not 8, we need to write out correctly-sized embed_bytes
2991 // and correctly account for the target's endianness
2992 const writer = pp.comp.generated_buf.writer(pp.gpa);
2993
2994 {
2995 const byte = embed_bytes[0];
2996 const start = pp.comp.generated_buf.items.len;
2997 try writer.print("{d}", .{byte});
2998 pp.addTokenAssumeCapacity(try pp.makeGeneratedToken(start, .embed_byte, filename_tok));
2999 }
3000
3001 for (embed_bytes[1..]) |byte| {
3002 const start = pp.comp.generated_buf.items.len;
3003 try writer.print(",{d}", .{byte});
3004 pp.addTokenAssumeCapacity(.{ .id = .comma, .loc = .{ .id = .generated, .byte_offset = @intCast(start) } });
3005 pp.addTokenAssumeCapacity(try pp.makeGeneratedToken(start + 1, .embed_byte, filename_tok));
3006 }
3007 try pp.comp.generated_buf.append(pp.gpa, '\n');
3008
3009 try Range.expand(suffix, pp, tokenizer);
3010}
3011
3012// Handle a #include directive.
3013fn include(pp: *Preprocessor, tokenizer: *Tokenizer, which: Compilation.WhichInclude) MacroError!void {
3014 const first = tokenizer.nextNoWS();
3015 const new_source = findIncludeSource(pp, tokenizer, first, which) catch |er| switch (er) {
3016 error.InvalidInclude => return,
3017 else => |e| return e,
3018 };
3019
3020 // Prevent stack overflow
3021 pp.include_depth += 1;
3022 defer pp.include_depth -= 1;
3023 if (pp.include_depth > max_include_depth) {
3024 try pp.comp.addDiagnostic(.{
3025 .tag = .too_many_includes,
3026 .loc = .{ .id = first.source, .byte_offset = first.start, .line = first.line },
3027 }, &.{});
3028 return error.StopPreprocessing;
3029 }
3030
3031 if (pp.include_guards.get(new_source.id)) |guard| {
3032 if (pp.defines.contains(guard)) return;
3033 }
3034
3035 if (pp.verbose) {
3036 pp.verboseLog(first, "include file {s}", .{new_source.path});
3037 }
3038
3039 const token_state = pp.getTokenState();
3040 try pp.addIncludeStart(new_source);
3041 const eof = pp.preprocessExtra(new_source) catch |er| switch (er) {
3042 error.StopPreprocessing => {
3043 for (pp.expansion_entries.items(.locs)[token_state.expansion_entries_len..]) |loc| TokenWithExpansionLocs.free(loc, pp.gpa);
3044 pp.restoreTokenState(token_state);
3045 return;
3046 },
3047 else => |e| return e,
3048 };
3049 try eof.checkMsEof(new_source, pp.comp);
3050 if (pp.preserve_whitespace and pp.tokens.items(.id)[pp.tokens.len - 1] != .nl) {
3051 try pp.addToken(.{ .id = .nl, .loc = .{
3052 .id = tokenizer.source,
3053 .line = tokenizer.line,
3054 } });
3055 }
3056 if (pp.linemarkers == .none) return;
3057 var next = first;
3058 while (true) {
3059 var tmp = tokenizer.*;
3060 next = tmp.nextNoWS();
3061 if (next.id != .nl) break;
3062 tokenizer.* = tmp;
3063 }
3064 try pp.addIncludeResume(next.source, next.end, next.line);
3065}
3066
3067/// tokens that are part of a pragma directive can happen in 3 ways:
3068/// 1. directly in the text via `#pragma ...`
3069/// 2. Via a string literal argument to `_Pragma`
3070/// 3. Via a stringified macro argument which is used as an argument to `_Pragma`
3071/// operator_loc: Location of `_Pragma`; null if this is from #pragma
3072/// arg_locs: expansion locations of the argument to _Pragma. empty if #pragma or a raw string literal was used
3073fn makePragmaToken(pp: *Preprocessor, raw: RawToken, operator_loc: ?Source.Location, arg_locs: []const Source.Location) !TokenWithExpansionLocs {
3074 var tok = tokFromRaw(raw);
3075 if (operator_loc) |loc| {
3076 try tok.addExpansionLocation(pp.gpa, &.{loc});
3077 }
3078 try tok.addExpansionLocation(pp.gpa, arg_locs);
3079 return tok;
3080}
3081
3082pub fn addToken(pp: *Preprocessor, tok: TokenWithExpansionLocs) !void {
3083 if (tok.expansion_locs) |expansion_locs| {
3084 try pp.expansion_entries.append(pp.gpa, .{ .idx = @intCast(pp.tokens.len), .locs = expansion_locs });
3085 }
3086 try pp.tokens.append(pp.gpa, .{ .id = tok.id, .loc = tok.loc });
3087}
3088
3089pub fn addTokenAssumeCapacity(pp: *Preprocessor, tok: TokenWithExpansionLocs) void {
3090 if (tok.expansion_locs) |expansion_locs| {
3091 pp.expansion_entries.appendAssumeCapacity(.{ .idx = @intCast(pp.tokens.len), .locs = expansion_locs });
3092 }
3093 pp.tokens.appendAssumeCapacity(.{ .id = tok.id, .loc = tok.loc });
3094}
3095
3096pub fn ensureTotalTokenCapacity(pp: *Preprocessor, capacity: usize) !void {
3097 try pp.tokens.ensureTotalCapacity(pp.gpa, capacity);
3098 try pp.expansion_entries.ensureTotalCapacity(pp.gpa, capacity);
3099}
3100
3101pub fn ensureUnusedTokenCapacity(pp: *Preprocessor, capacity: usize) !void {
3102 try pp.tokens.ensureUnusedCapacity(pp.gpa, capacity);
3103 try pp.expansion_entries.ensureUnusedCapacity(pp.gpa, capacity);
3104}
3105
3106/// Handle a pragma directive
3107fn pragma(pp: *Preprocessor, tokenizer: *Tokenizer, pragma_tok: RawToken, operator_loc: ?Source.Location, arg_locs: []const Source.Location) !void {
3108 const name_tok = tokenizer.nextNoWS();
3109 if (name_tok.id == .nl or name_tok.id == .eof) return;
3110
3111 const name = pp.tokSlice(name_tok);
3112 try pp.addToken(try pp.makePragmaToken(pragma_tok, operator_loc, arg_locs));
3113 const pragma_start: u32 = @intCast(pp.tokens.len);
3114
3115 const pragma_name_tok = try pp.makePragmaToken(name_tok, operator_loc, arg_locs);
3116 try pp.addToken(pragma_name_tok);
3117 while (true) {
3118 const next_tok = tokenizer.next();
3119 if (next_tok.id == .whitespace) continue;
3120 if (next_tok.id == .eof) {
3121 try pp.addToken(.{
3122 .id = .nl,
3123 .loc = .{ .id = .generated },
3124 });
3125 break;
3126 }
3127 try pp.addToken(try pp.makePragmaToken(next_tok, operator_loc, arg_locs));
3128 if (next_tok.id == .nl) break;
3129 }
3130 if (pp.comp.getPragma(name)) |prag| unknown: {
3131 return prag.preprocessorCB(pp, pragma_start) catch |er| switch (er) {
3132 error.UnknownPragma => break :unknown,
3133 else => |e| return e,
3134 };
3135 }
3136 return pp.comp.addDiagnostic(.{
3137 .tag = .unknown_pragma,
3138 .loc = pragma_name_tok.loc,
3139 }, pragma_name_tok.expansionSlice());
3140}
3141
3142fn findIncludeFilenameToken(
3143 pp: *Preprocessor,
3144 first_token: RawToken,
3145 tokenizer: *Tokenizer,
3146 trailing_token_behavior: enum { ignore_trailing_tokens, expect_nl_eof },
3147) !TokenWithExpansionLocs {
3148 var first = first_token;
3149
3150 if (first.id == .angle_bracket_left) to_end: {
3151 // The tokenizer does not handle <foo> include strings so do it here.
3152 while (tokenizer.index < tokenizer.buf.len) : (tokenizer.index += 1) {
3153 switch (tokenizer.buf[tokenizer.index]) {
3154 '>' => {
3155 tokenizer.index += 1;
3156 first.end = tokenizer.index;
3157 first.id = .macro_string;
3158 break :to_end;
3159 },
3160 '\n' => break,
3161 else => {},
3162 }
3163 }
3164 try pp.comp.addDiagnostic(.{
3165 .tag = .header_str_closing,
3166 .loc = .{ .id = first.source, .byte_offset = tokenizer.index, .line = first.line },
3167 }, &.{});
3168 try pp.err(first, .header_str_match);
3169 }
3170
3171 const source_tok = tokFromRaw(first);
3172 const filename_tok, const expanded_trailing = switch (source_tok.id) {
3173 .string_literal, .macro_string => .{ source_tok, false },
3174 else => expanded: {
3175 // Try to expand if the argument is a macro.
3176 pp.top_expansion_buf.items.len = 0;
3177 defer for (pp.top_expansion_buf.items) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
3178 try pp.top_expansion_buf.append(source_tok);
3179 pp.expansion_source_loc = source_tok.loc;
3180
3181 try pp.expandMacroExhaustive(tokenizer, &pp.top_expansion_buf, 0, 1, true, .non_expr);
3182 var trailing_toks: []const TokenWithExpansionLocs = &.{};
3183 const include_str = (try pp.reconstructIncludeString(pp.top_expansion_buf.items, &trailing_toks, tokFromRaw(first))) orelse {
3184 try pp.expectNl(tokenizer);
3185 return error.InvalidInclude;
3186 };
3187 const start = pp.comp.generated_buf.items.len;
3188 try pp.comp.generated_buf.appendSlice(pp.gpa, include_str);
3189
3190 break :expanded .{ try pp.makeGeneratedToken(start, switch (include_str[0]) {
3191 '"' => .string_literal,
3192 '<' => .macro_string,
3193 else => unreachable,
3194 }, pp.top_expansion_buf.items[0]), trailing_toks.len != 0 };
3195 },
3196 };
3197
3198 switch (trailing_token_behavior) {
3199 .expect_nl_eof => {
3200 // Error on extra tokens.
3201 const nl = tokenizer.nextNoWS();
3202 if ((nl.id != .nl and nl.id != .eof) or expanded_trailing) {
3203 skipToNl(tokenizer);
3204 try pp.comp.diagnostics.addExtra(pp.comp.langopts, .{
3205 .tag = .extra_tokens_directive_end,
3206 .loc = filename_tok.loc,
3207 }, filename_tok.expansionSlice(), false);
3208 }
3209 },
3210 .ignore_trailing_tokens => if (expanded_trailing) {
3211 try pp.comp.diagnostics.addExtra(pp.comp.langopts, .{
3212 .tag = .extra_tokens_directive_end,
3213 .loc = filename_tok.loc,
3214 }, filename_tok.expansionSlice(), false);
3215 },
3216 }
3217 return filename_tok;
3218}
3219
3220fn findIncludeSource(pp: *Preprocessor, tokenizer: *Tokenizer, first: RawToken, which: Compilation.WhichInclude) !Source {
3221 const filename_tok = try pp.findIncludeFilenameToken(first, tokenizer, .expect_nl_eof);
3222 defer TokenWithExpansionLocs.free(filename_tok.expansion_locs, pp.gpa);
3223
3224 // Check for empty filename.
3225 const tok_slice = pp.expandedSliceExtra(filename_tok, .single_macro_ws);
3226 if (tok_slice.len < 3) {
3227 try pp.err(first, .empty_filename);
3228 return error.InvalidInclude;
3229 }
3230
3231 // Find the file.
3232 const filename = tok_slice[1 .. tok_slice.len - 1];
3233 const include_type: Compilation.IncludeType = switch (filename_tok.id) {
3234 .string_literal => .quotes,
3235 .macro_string => .angle_brackets,
3236 else => unreachable,
3237 };
3238
3239 return (try pp.comp.findInclude(filename, first, include_type, which)) orelse
3240 return pp.fatalNotFound(filename_tok, filename);
3241}
3242
3243fn printLinemarker(
3244 pp: *Preprocessor,
3245 w: anytype,
3246 line_no: u32,
3247 source: Source,
3248 start_resume: enum(u8) { start, @"resume", none },
3249) !void {
3250 try w.writeByte('#');
3251 if (pp.linemarkers == .line_directives) try w.writeAll("line");
3252 try w.print(" {d} \"", .{line_no});
3253 for (source.path) |byte| switch (byte) {
3254 '\n' => try w.writeAll("\\n"),
3255 '\r' => try w.writeAll("\\r"),
3256 '\t' => try w.writeAll("\\t"),
3257 '\\' => try w.writeAll("\\\\"),
3258 '"' => try w.writeAll("\\\""),
3259 ' ', '!', '#'...'&', '('...'[', ']'...'~' => try w.writeByte(byte),
3260 // Use hex escapes for any non-ASCII/unprintable characters.
3261 // This ensures that the parsed version of this string will end up
3262 // containing the same bytes as the input regardless of encoding.
3263 else => {
3264 try w.writeAll("\\x");
3265 try std.fmt.formatInt(byte, 16, .lower, .{ .width = 2, .fill = '0' }, w);
3266 },
3267 };
3268 try w.writeByte('"');
3269 if (pp.linemarkers == .numeric_directives) {
3270 switch (start_resume) {
3271 .none => {},
3272 .start => try w.writeAll(" 1"),
3273 .@"resume" => try w.writeAll(" 2"),
3274 }
3275 switch (source.kind) {
3276 .user => {},
3277 .system => try w.writeAll(" 3"),
3278 .extern_c_system => try w.writeAll(" 3 4"),
3279 }
3280 }
3281 try w.writeByte('\n');
3282}
3283
3284// After how many empty lines are needed to replace them with linemarkers.
3285const collapse_newlines = 8;
3286
3287pub const DumpMode = enum {
3288 /// Standard preprocessor output; no macros
3289 result_only,
3290 /// Output only #define directives for all the macros defined during the execution of the preprocessor
3291 /// Only macros which are still defined at the end of preprocessing are printed.
3292 /// Only the most recent definition is printed
3293 /// Defines are printed in arbitrary order
3294 macros_only,
3295 /// Standard preprocessor output; but additionally output #define's and #undef's for macros as they are encountered
3296 macros_and_result,
3297 /// Same as macros_and_result, except only the macro name is printed for #define's
3298 macro_names_and_result,
3299};
3300
3301/// Pretty-print the macro define or undef at location `loc`.
3302/// We re-tokenize the directive because we are printing a macro that may have the same name as one in
3303/// `pp.defines` but a different definition (due to being #undef'ed and then redefined)
3304fn prettyPrintMacro(pp: *Preprocessor, w: anytype, loc: Source.Location, parts: enum { name_only, name_and_body }) !void {
3305 const source = pp.comp.getSource(loc.id);
3306 var tokenizer: Tokenizer = .{
3307 .buf = source.buf,
3308 .langopts = pp.comp.langopts,
3309 .source = source.id,
3310 .index = loc.byte_offset,
3311 };
3312 var prev_ws = false; // avoid printing multiple whitespace if /* */ comments are within the macro def
3313 var saw_name = false; // do not print comments before the name token is seen.
3314 while (true) {
3315 const tok = tokenizer.next();
3316 switch (tok.id) {
3317 .comment => {
3318 if (saw_name) {
3319 prev_ws = false;
3320 try w.print("{s}", .{pp.tokSlice(tok)});
3321 }
3322 },
3323 .nl, .eof => break,
3324 .whitespace => {
3325 if (!prev_ws) {
3326 try w.writeByte(' ');
3327 prev_ws = true;
3328 }
3329 },
3330 else => {
3331 prev_ws = false;
3332 try w.print("{s}", .{pp.tokSlice(tok)});
3333 },
3334 }
3335 if (tok.id == .identifier or tok.id == .extended_identifier) {
3336 if (parts == .name_only) break;
3337 saw_name = true;
3338 }
3339 }
3340}
3341
3342fn prettyPrintMacrosOnly(pp: *Preprocessor, w: anytype) !void {
3343 var it = pp.defines.valueIterator();
3344 while (it.next()) |macro| {
3345 if (macro.is_builtin) continue;
3346
3347 try w.writeAll("#define ");
3348 try pp.prettyPrintMacro(w, macro.loc, .name_and_body);
3349 try w.writeByte('\n');
3350 }
3351}
3352
3353/// Pretty print tokens and try to preserve whitespace.
3354pub fn prettyPrintTokens(pp: *Preprocessor, w: anytype, macro_dump_mode: DumpMode) !void {
3355 if (macro_dump_mode == .macros_only) {
3356 return pp.prettyPrintMacrosOnly(w);
3357 }
3358
3359 const tok_ids = pp.tokens.items(.id);
3360
3361 var i: u32 = 0;
3362 var last_nl = true;
3363 outer: while (true) : (i += 1) {
3364 var cur: Token = pp.tokens.get(i);
3365 switch (cur.id) {
3366 .eof => {
3367 if (!last_nl) try w.writeByte('\n');
3368 return;
3369 },
3370 .nl => {
3371 var newlines: u32 = 0;
3372 for (tok_ids[i..], i..) |id, j| {
3373 if (id == .nl) {
3374 newlines += 1;
3375 } else if (id == .eof) {
3376 if (!last_nl) try w.writeByte('\n');
3377 return;
3378 } else if (id != .whitespace) {
3379 if (pp.linemarkers == .none) {
3380 if (newlines < 2) break;
3381 } else if (newlines < collapse_newlines) {
3382 break;
3383 }
3384
3385 i = @intCast((j - 1) - @intFromBool(tok_ids[j - 1] == .whitespace));
3386 if (!last_nl) try w.writeAll("\n");
3387 if (pp.linemarkers != .none) {
3388 const next = pp.tokens.get(i);
3389 const source = pp.comp.getSource(next.loc.id);
3390 const line_col = source.lineCol(next.loc);
3391 try pp.printLinemarker(w, line_col.line_no, source, .none);
3392 last_nl = true;
3393 }
3394 continue :outer;
3395 }
3396 }
3397 last_nl = true;
3398 try w.writeAll("\n");
3399 },
3400 .keyword_pragma => {
3401 const pragma_name = pp.expandedSlice(pp.tokens.get(i + 1));
3402 const end_idx = mem.indexOfScalarPos(Token.Id, tok_ids, i, .nl) orelse i + 1;
3403 const pragma_len = @as(u32, @intCast(end_idx)) - i;
3404
3405 if (pp.comp.getPragma(pragma_name)) |prag| {
3406 if (!prag.shouldPreserveTokens(pp, i + 1)) {
3407 try w.writeByte('\n');
3408 i += pragma_len;
3409 cur = pp.tokens.get(i);
3410 continue;
3411 }
3412 }
3413 try w.writeAll("#pragma");
3414 i += 1;
3415 while (true) : (i += 1) {
3416 cur = pp.tokens.get(i);
3417 if (cur.id == .nl) {
3418 try w.writeByte('\n');
3419 last_nl = true;
3420 break;
3421 }
3422 try w.writeByte(' ');
3423 const slice = pp.expandedSlice(cur);
3424 try w.writeAll(slice);
3425 }
3426 },
3427 .whitespace => {
3428 var slice = pp.expandedSlice(cur);
3429 while (mem.indexOfScalar(u8, slice, '\n')) |some| {
3430 if (pp.linemarkers != .none) try w.writeByte('\n');
3431 slice = slice[some + 1 ..];
3432 }
3433 for (slice) |_| try w.writeByte(' ');
3434 last_nl = false;
3435 },
3436 .include_start => {
3437 const source = pp.comp.getSource(cur.loc.id);
3438
3439 try pp.printLinemarker(w, 1, source, .start);
3440 last_nl = true;
3441 },
3442 .include_resume => {
3443 const source = pp.comp.getSource(cur.loc.id);
3444 const line_col = source.lineCol(cur.loc);
3445 if (!last_nl) try w.writeAll("\n");
3446
3447 try pp.printLinemarker(w, line_col.line_no, source, .@"resume");
3448 last_nl = true;
3449 },
3450 .keyword_define, .keyword_undef => {
3451 switch (macro_dump_mode) {
3452 .macros_and_result, .macro_names_and_result => {
3453 try w.writeByte('#');
3454 try pp.prettyPrintMacro(w, cur.loc, if (macro_dump_mode == .macros_and_result) .name_and_body else .name_only);
3455 last_nl = false;
3456 },
3457 .result_only => unreachable, // `pp.store_macro_tokens` should be false for standard preprocessor output
3458 .macros_only => unreachable, // handled by prettyPrintMacrosOnly
3459 }
3460 },
3461 else => {
3462 const slice = pp.expandedSlice(cur);
3463 try w.writeAll(slice);
3464 last_nl = false;
3465 },
3466 }
3467 }
3468}
3469
3470test "Preserve pragma tokens sometimes" {
3471 const allocator = std.testing.allocator;
3472 const Test = struct {
3473 fn runPreprocessor(source_text: []const u8) ![]const u8 {
3474 var buf = std.ArrayList(u8).init(allocator);
3475 defer buf.deinit();
3476
3477 var comp = Compilation.init(allocator, std.fs.cwd());
3478 defer comp.deinit();
3479
3480 try comp.addDefaultPragmaHandlers();
3481
3482 var pp = Preprocessor.init(&comp);
3483 defer pp.deinit();
3484
3485 pp.preserve_whitespace = true;
3486 assert(pp.linemarkers == .none);
3487
3488 const test_runner_macros = try comp.addSourceFromBuffer("<test_runner>", source_text);
3489 const eof = try pp.preprocess(test_runner_macros);
3490 try pp.addToken(eof);
3491 try pp.prettyPrintTokens(buf.writer(), .result_only);
3492 return allocator.dupe(u8, buf.items);
3493 }
3494
3495 fn check(source_text: []const u8, expected: []const u8) !void {
3496 const output = try runPreprocessor(source_text);
3497 defer allocator.free(output);
3498
3499 try std.testing.expectEqualStrings(expected, output);
3500 }
3501 };
3502 const preserve_gcc_diagnostic =
3503 \\#pragma GCC diagnostic error "-Wnewline-eof"
3504 \\#pragma GCC warning error "-Wnewline-eof"
3505 \\int x;
3506 \\#pragma GCC ignored error "-Wnewline-eof"
3507 \\
3508 ;
3509 try Test.check(preserve_gcc_diagnostic, preserve_gcc_diagnostic);
3510
3511 const omit_once =
3512 \\#pragma once
3513 \\int x;
3514 \\#pragma once
3515 \\
3516 ;
3517 // TODO should only be one newline afterwards when emulating clang
3518 try Test.check(omit_once, "\nint x;\n\n");
3519
3520 const omit_poison =
3521 \\#pragma GCC poison foobar
3522 \\
3523 ;
3524 try Test.check(omit_poison, "\n");
3525}
3526
3527test "destringify" {
3528 const allocator = std.testing.allocator;
3529 const Test = struct {
3530 fn testDestringify(pp: *Preprocessor, stringified: []const u8, destringified: []const u8) !void {
3531 pp.char_buf.clearRetainingCapacity();
3532 try pp.char_buf.ensureUnusedCapacity(stringified.len);
3533 pp.destringify(stringified);
3534 try std.testing.expectEqualStrings(destringified, pp.char_buf.items);
3535 }
3536 };
3537 var comp = Compilation.init(allocator, std.fs.cwd());
3538 defer comp.deinit();
3539 var pp = Preprocessor.init(&comp);
3540 defer pp.deinit();
3541
3542 try Test.testDestringify(&pp, "hello\tworld\n", "hello\tworld\n");
3543 try Test.testDestringify(&pp,
3544 \\ \"FOO BAR BAZ\"
3545 ,
3546 \\ "FOO BAR BAZ"
3547 );
3548 try Test.testDestringify(&pp,
3549 \\ \\t\\n
3550 \\
3551 ,
3552 \\ \t\n
3553 \\
3554 );
3555}
3556
3557test "Include guards" {
3558 const Test = struct {
3559 /// This is here so that when #elifdef / #elifndef are added we don't forget
3560 /// to test that they don't accidentally break include guard detection
3561 fn pairsWithIfndef(tok_id: RawToken.Id) bool {
3562 return switch (tok_id) {
3563 .keyword_elif,
3564 .keyword_elifdef,
3565 .keyword_elifndef,
3566 .keyword_else,
3567 => true,
3568
3569 .keyword_include,
3570 .keyword_include_next,
3571 .keyword_embed,
3572 .keyword_define,
3573 .keyword_defined,
3574 .keyword_undef,
3575 .keyword_ifdef,
3576 .keyword_ifndef,
3577 .keyword_error,
3578 .keyword_warning,
3579 .keyword_pragma,
3580 .keyword_line,
3581 .keyword_endif,
3582 => false,
3583 else => unreachable,
3584 };
3585 }
3586
3587 fn skippable(tok_id: RawToken.Id) bool {
3588 return switch (tok_id) {
3589 .keyword_defined, .keyword_va_args, .keyword_va_opt, .keyword_endif => true,
3590 else => false,
3591 };
3592 }
3593
3594 fn testIncludeGuard(allocator: std.mem.Allocator, comptime template: []const u8, tok_id: RawToken.Id, expected_guards: u32) !void {
3595 var comp = Compilation.init(allocator, std.fs.cwd());
3596 defer comp.deinit();
3597 var pp = Preprocessor.init(&comp);
3598 defer pp.deinit();
3599
3600 const path = try std.fs.path.join(allocator, &.{ ".", "bar.h" });
3601 defer allocator.free(path);
3602
3603 _ = try comp.addSourceFromBuffer(path, "int bar = 5;\n");
3604
3605 var buf = std.ArrayList(u8).init(allocator);
3606 defer buf.deinit();
3607
3608 var writer = buf.writer();
3609 switch (tok_id) {
3610 .keyword_include, .keyword_include_next => try writer.print(template, .{ tok_id.lexeme().?, " \"bar.h\"" }),
3611 .keyword_define, .keyword_undef => try writer.print(template, .{ tok_id.lexeme().?, " BAR" }),
3612 .keyword_ifndef,
3613 .keyword_ifdef,
3614 .keyword_elifdef,
3615 .keyword_elifndef,
3616 => try writer.print(template, .{ tok_id.lexeme().?, " BAR\n#endif" }),
3617 else => try writer.print(template, .{ tok_id.lexeme().?, "" }),
3618 }
3619 const source = try comp.addSourceFromBuffer("test.h", buf.items);
3620 _ = try pp.preprocess(source);
3621
3622 try std.testing.expectEqual(expected_guards, pp.include_guards.count());
3623 }
3624 };
3625 const tags = std.meta.tags(RawToken.Id);
3626 for (tags) |tag| {
3627 if (Test.skippable(tag)) continue;
3628 var copy = tag;
3629 copy.simplifyMacroKeyword();
3630 if (copy != tag or tag == .keyword_else) {
3631 const inside_ifndef_template =
3632 \\//Leading comment (should be ignored)
3633 \\
3634 \\#ifndef FOO
3635 \\#{s}{s}
3636 \\#endif
3637 ;
3638 const expected_guards: u32 = if (Test.pairsWithIfndef(tag)) 0 else 1;
3639 try Test.testIncludeGuard(std.testing.allocator, inside_ifndef_template, tag, expected_guards);
3640
3641 const outside_ifndef_template =
3642 \\#ifndef FOO
3643 \\#endif
3644 \\#{s}{s}
3645 ;
3646 try Test.testIncludeGuard(std.testing.allocator, outside_ifndef_template, tag, 0);
3647 }
3648 }
3649}
lib/compiler/aro/aro/Source.zig deleted-137
...@@ -1,137 +0,0 @@
1const std = @import("std");
2
3pub const Id = enum(u32) {
4 unused = 0,
5 generated = 1,
6 _,
7};
8
9/// Classifies the file for line marker output in -E mode
10pub const Kind = enum {
11 /// regular file
12 user,
13 /// Included from a system include directory
14 system,
15 /// Included from an "implicit extern C" directory
16 extern_c_system,
17};
18
19pub const Location = struct {
20 id: Id = .unused,
21 byte_offset: u32 = 0,
22 line: u32 = 0,
23
24 pub fn eql(a: Location, b: Location) bool {
25 return a.id == b.id and a.byte_offset == b.byte_offset and a.line == b.line;
26 }
27};
28
29const Source = @This();
30
31path: []const u8,
32buf: []const u8,
33id: Id,
34/// each entry represents a byte position within `buf` where a backslash+newline was deleted
35/// from the original raw buffer. The same position can appear multiple times if multiple
36/// consecutive splices happened. Guaranteed to be non-decreasing
37splice_locs: []const u32,
38kind: Kind,
39
40/// Todo: binary search instead of scanning entire `splice_locs`.
41pub fn numSplicesBefore(source: Source, byte_offset: u32) u32 {
42 for (source.splice_locs, 0..) |splice_offset, i| {
43 if (splice_offset > byte_offset) return @intCast(i);
44 }
45 return @intCast(source.splice_locs.len);
46}
47
48/// Returns the actual line number (before newline splicing) of a Location
49/// This corresponds to what the user would actually see in their text editor
50pub fn physicalLine(source: Source, loc: Location) u32 {
51 return loc.line + source.numSplicesBefore(loc.byte_offset);
52}
53
54const LineCol = struct { line: []const u8, line_no: u32, col: u32, width: u32, end_with_splice: bool };
55
56pub fn lineCol(source: Source, loc: Location) LineCol {
57 var start: usize = 0;
58 // find the start of the line which is either a newline or a splice
59 if (std.mem.lastIndexOfScalar(u8, source.buf[0..loc.byte_offset], '\n')) |some| start = some + 1;
60 const splice_index: u32 = for (source.splice_locs, 0..) |splice_offset, i| {
61 if (splice_offset > start) {
62 if (splice_offset < loc.byte_offset) {
63 start = splice_offset;
64 break @as(u32, @intCast(i)) + 1;
65 }
66 break @intCast(i);
67 }
68 } else @intCast(source.splice_locs.len);
69 var i: usize = start;
70 var col: u32 = 1;
71 var width: u32 = 0;
72
73 while (i < loc.byte_offset) : (col += 1) { // TODO this is still incorrect, but better
74 const len = std.unicode.utf8ByteSequenceLength(source.buf[i]) catch {
75 i += 1;
76 continue;
77 };
78 const slice = source.buf[i..];
79 if (len > slice.len) {
80 break;
81 }
82 const cp = switch (len) {
83 1 => slice[0],
84 2 => std.unicode.utf8Decode2(slice[0..2].*),
85 3 => std.unicode.utf8Decode3(slice[0..3].*),
86 4 => std.unicode.utf8Decode4(slice[0..4].*),
87 else => unreachable,
88 } catch {
89 i += 1;
90 continue;
91 };
92 width += codepointWidth(cp);
93 i += len;
94 }
95
96 // find the end of the line which is either a newline, EOF or a splice
97 var nl = source.buf.len;
98 var end_with_splice = false;
99 if (std.mem.indexOfScalar(u8, source.buf[start..], '\n')) |some| nl = some + start;
100 if (source.splice_locs.len > splice_index and nl > source.splice_locs[splice_index] and source.splice_locs[splice_index] > start) {
101 end_with_splice = true;
102 nl = source.splice_locs[splice_index];
103 }
104 return .{
105 .line = source.buf[start..nl],
106 .line_no = loc.line + splice_index,
107 .col = col,
108 .width = width,
109 .end_with_splice = end_with_splice,
110 };
111}
112
113fn codepointWidth(cp: u32) u32 {
114 return switch (cp) {
115 0x1100...0x115F,
116 0x2329,
117 0x232A,
118 0x2E80...0x303F,
119 0x3040...0x3247,
120 0x3250...0x4DBF,
121 0x4E00...0xA4C6,
122 0xA960...0xA97C,
123 0xAC00...0xD7A3,
124 0xF900...0xFAFF,
125 0xFE10...0xFE19,
126 0xFE30...0xFE6B,
127 0xFF01...0xFF60,
128 0xFFE0...0xFFE6,
129 0x1B000...0x1B001,
130 0x1F200...0x1F251,
131 0x20000...0x3FFFD,
132 0x1F300...0x1F5FF,
133 0x1F900...0x1F9FF,
134 => 2,
135 else => 1,
136 };
137}
lib/compiler/aro/aro/StringInterner.zig deleted-83
...@@ -1,83 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const Compilation = @import("Compilation.zig");
4
5const StringToIdMap = std.StringHashMapUnmanaged(StringId);
6
7pub const StringId = enum(u32) {
8 empty,
9 _,
10};
11
12pub const TypeMapper = struct {
13 const LookupSpeed = enum {
14 fast,
15 slow,
16 };
17
18 data: union(LookupSpeed) {
19 fast: []const []const u8,
20 slow: *const StringToIdMap,
21 },
22
23 pub fn lookup(self: TypeMapper, string_id: StringInterner.StringId) []const u8 {
24 if (string_id == .empty) return "";
25 switch (self.data) {
26 .fast => |arr| return arr[@intFromEnum(string_id)],
27 .slow => |map| {
28 var it = map.iterator();
29 while (it.next()) |entry| {
30 if (entry.value_ptr.* == string_id) return entry.key_ptr.*;
31 }
32 unreachable;
33 },
34 }
35 }
36
37 pub fn deinit(self: TypeMapper, allocator: mem.Allocator) void {
38 switch (self.data) {
39 .slow => {},
40 .fast => |arr| allocator.free(arr),
41 }
42 }
43};
44
45const StringInterner = @This();
46
47string_table: StringToIdMap = .{},
48next_id: StringId = @enumFromInt(@intFromEnum(StringId.empty) + 1),
49
50pub fn deinit(self: *StringInterner, allocator: mem.Allocator) void {
51 self.string_table.deinit(allocator);
52}
53
54pub fn intern(comp: *Compilation, str: []const u8) !StringId {
55 return comp.string_interner.internExtra(comp.gpa, str);
56}
57
58pub fn internExtra(self: *StringInterner, allocator: mem.Allocator, str: []const u8) !StringId {
59 if (str.len == 0) return .empty;
60
61 const gop = try self.string_table.getOrPut(allocator, str);
62 if (gop.found_existing) return gop.value_ptr.*;
63
64 defer self.next_id = @enumFromInt(@intFromEnum(self.next_id) + 1);
65 gop.value_ptr.* = self.next_id;
66 return self.next_id;
67}
68
69/// deinit for the returned TypeMapper is a no-op and does not need to be called
70pub fn getSlowTypeMapper(self: *const StringInterner) TypeMapper {
71 return TypeMapper{ .data = .{ .slow = &self.string_table } };
72}
73
74/// Caller must call `deinit` on the returned TypeMapper
75pub fn getFastTypeMapper(self: *const StringInterner, allocator: mem.Allocator) !TypeMapper {
76 var strings = try allocator.alloc([]const u8, @intFromEnum(self.next_id));
77 var it = self.string_table.iterator();
78 strings[0] = "";
79 while (it.next()) |entry| {
80 strings[@intFromEnum(entry.value_ptr.*)] = entry.key_ptr.*;
81 }
82 return TypeMapper{ .data = .{ .fast = strings } };
83}
lib/compiler/aro/aro/SymbolStack.zig deleted-399
...@@ -1,399 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const Allocator = mem.Allocator;
4const assert = std.debug.assert;
5const Tree = @import("Tree.zig");
6const Token = Tree.Token;
7const TokenIndex = Tree.TokenIndex;
8const NodeIndex = Tree.NodeIndex;
9const Type = @import("Type.zig");
10const Parser = @import("Parser.zig");
11const Value = @import("Value.zig");
12const StringId = @import("StringInterner.zig").StringId;
13
14const SymbolStack = @This();
15
16pub const Symbol = struct {
17 name: StringId,
18 ty: Type,
19 tok: TokenIndex,
20 node: NodeIndex = .none,
21 kind: Kind,
22 val: Value,
23};
24
25pub const Kind = enum {
26 typedef,
27 @"struct",
28 @"union",
29 @"enum",
30 decl,
31 def,
32 enumeration,
33 constexpr,
34};
35
36scopes: std.ArrayListUnmanaged(Scope) = .empty,
37/// allocations from nested scopes are retained after popping; `active_len` is the number
38/// of currently-active items in `scopes`.
39active_len: usize = 0,
40
41const Scope = struct {
42 vars: std.AutoHashMapUnmanaged(StringId, Symbol) = .empty,
43 tags: std.AutoHashMapUnmanaged(StringId, Symbol) = .empty,
44
45 fn deinit(self: *Scope, allocator: Allocator) void {
46 self.vars.deinit(allocator);
47 self.tags.deinit(allocator);
48 }
49
50 fn clearRetainingCapacity(self: *Scope) void {
51 self.vars.clearRetainingCapacity();
52 self.tags.clearRetainingCapacity();
53 }
54};
55
56pub fn deinit(s: *SymbolStack, gpa: Allocator) void {
57 std.debug.assert(s.active_len == 0); // all scopes should have been popped
58 for (s.scopes.items) |*scope| {
59 scope.deinit(gpa);
60 }
61 s.scopes.deinit(gpa);
62 s.* = undefined;
63}
64
65pub fn pushScope(s: *SymbolStack, p: *Parser) !void {
66 if (s.active_len + 1 > s.scopes.items.len) {
67 try s.scopes.append(p.gpa, .{});
68 s.active_len = s.scopes.items.len;
69 } else {
70 s.scopes.items[s.active_len].clearRetainingCapacity();
71 s.active_len += 1;
72 }
73}
74
75pub fn popScope(s: *SymbolStack) void {
76 s.active_len -= 1;
77}
78
79pub fn findTypedef(s: *SymbolStack, p: *Parser, name: StringId, name_tok: TokenIndex, no_type_yet: bool) !?Symbol {
80 const prev = s.lookup(name, .vars) orelse s.lookup(name, .tags) orelse return null;
81 switch (prev.kind) {
82 .typedef => return prev,
83 .@"struct" => {
84 if (no_type_yet) return null;
85 try p.errStr(.must_use_struct, name_tok, p.tokSlice(name_tok));
86 return prev;
87 },
88 .@"union" => {
89 if (no_type_yet) return null;
90 try p.errStr(.must_use_union, name_tok, p.tokSlice(name_tok));
91 return prev;
92 },
93 .@"enum" => {
94 if (no_type_yet) return null;
95 try p.errStr(.must_use_enum, name_tok, p.tokSlice(name_tok));
96 return prev;
97 },
98 else => return null,
99 }
100}
101
102pub fn findSymbol(s: *SymbolStack, name: StringId) ?Symbol {
103 return s.lookup(name, .vars);
104}
105
106pub fn findTag(
107 s: *SymbolStack,
108 p: *Parser,
109 name: StringId,
110 kind: Token.Id,
111 name_tok: TokenIndex,
112 next_tok_id: Token.Id,
113) !?Symbol {
114 // `tag Name;` should always result in a new type if in a new scope.
115 const prev = (if (next_tok_id == .semicolon) s.get(name, .tags) else s.lookup(name, .tags)) orelse return null;
116 switch (prev.kind) {
117 .@"enum" => if (kind == .keyword_enum) return prev,
118 .@"struct" => if (kind == .keyword_struct) return prev,
119 .@"union" => if (kind == .keyword_union) return prev,
120 else => unreachable,
121 }
122 if (s.get(name, .tags) == null) return null;
123 try p.errStr(.wrong_tag, name_tok, p.tokSlice(name_tok));
124 try p.errTok(.previous_definition, prev.tok);
125 return null;
126}
127
128const ScopeKind = enum {
129 /// structs, enums, unions
130 tags,
131 /// everything else
132 vars,
133};
134
135/// Return the Symbol for `name` (or null if not found) in the innermost scope
136pub fn get(s: *SymbolStack, name: StringId, kind: ScopeKind) ?Symbol {
137 return switch (kind) {
138 .vars => s.scopes.items[s.active_len - 1].vars.get(name),
139 .tags => s.scopes.items[s.active_len - 1].tags.get(name),
140 };
141}
142
143/// Return the Symbol for `name` (or null if not found) in the nearest active scope,
144/// starting at the innermost.
145fn lookup(s: *SymbolStack, name: StringId, kind: ScopeKind) ?Symbol {
146 var i = s.active_len;
147 while (i > 0) {
148 i -= 1;
149 switch (kind) {
150 .vars => if (s.scopes.items[i].vars.get(name)) |sym| return sym,
151 .tags => if (s.scopes.items[i].tags.get(name)) |sym| return sym,
152 }
153 }
154 return null;
155}
156
157/// Define a symbol in the innermost scope. Does not issue diagnostics or check correctness
158/// with regard to the C standard.
159pub fn define(s: *SymbolStack, allocator: Allocator, symbol: Symbol) !void {
160 switch (symbol.kind) {
161 .constexpr, .def, .decl, .enumeration, .typedef => {
162 try s.scopes.items[s.active_len - 1].vars.put(allocator, symbol.name, symbol);
163 },
164 .@"struct", .@"union", .@"enum" => {
165 try s.scopes.items[s.active_len - 1].tags.put(allocator, symbol.name, symbol);
166 },
167 }
168}
169
170pub fn defineTypedef(
171 s: *SymbolStack,
172 p: *Parser,
173 name: StringId,
174 ty: Type,
175 tok: TokenIndex,
176 node: NodeIndex,
177) !void {
178 if (s.get(name, .vars)) |prev| {
179 switch (prev.kind) {
180 .typedef => {
181 if (!prev.ty.is(.invalid)) {
182 if (!ty.eql(prev.ty, p.comp, true)) {
183 try p.errStr(.redefinition_of_typedef, tok, try p.typePairStrExtra(ty, " vs ", prev.ty));
184 if (prev.tok != 0) try p.errTok(.previous_definition, prev.tok);
185 }
186 }
187 },
188 .enumeration, .decl, .def, .constexpr => {
189 try p.errStr(.redefinition_different_sym, tok, p.tokSlice(tok));
190 try p.errTok(.previous_definition, prev.tok);
191 },
192 else => unreachable,
193 }
194 }
195 try s.define(p.gpa, .{
196 .kind = .typedef,
197 .name = name,
198 .tok = tok,
199 .ty = .{
200 .name = name,
201 .specifier = ty.specifier,
202 .qual = ty.qual,
203 .data = ty.data,
204 },
205 .node = node,
206 .val = .{},
207 });
208}
209
210pub fn defineSymbol(
211 s: *SymbolStack,
212 p: *Parser,
213 name: StringId,
214 ty: Type,
215 tok: TokenIndex,
216 node: NodeIndex,
217 val: Value,
218 constexpr: bool,
219) !void {
220 if (s.get(name, .vars)) |prev| {
221 switch (prev.kind) {
222 .enumeration => {
223 try p.errStr(.redefinition_different_sym, tok, p.tokSlice(tok));
224 try p.errTok(.previous_definition, prev.tok);
225 },
226 .decl => {
227 if (!ty.eql(prev.ty, p.comp, true)) {
228 try p.errStr(.redefinition_incompatible, tok, p.tokSlice(tok));
229 try p.errTok(.previous_definition, prev.tok);
230 }
231 },
232 .def, .constexpr => {
233 try p.errStr(.redefinition, tok, p.tokSlice(tok));
234 try p.errTok(.previous_definition, prev.tok);
235 },
236 .typedef => {
237 try p.errStr(.redefinition_different_sym, tok, p.tokSlice(tok));
238 try p.errTok(.previous_definition, prev.tok);
239 },
240 else => unreachable,
241 }
242 }
243
244 try s.define(p.gpa, .{
245 .kind = if (constexpr) .constexpr else .def,
246 .name = name,
247 .tok = tok,
248 .ty = ty,
249 .node = node,
250 .val = val,
251 });
252}
253
254/// Get a pointer to the named symbol in the innermost scope.
255/// Asserts that a symbol with the name exists.
256pub fn getPtr(s: *SymbolStack, name: StringId, kind: ScopeKind) *Symbol {
257 return switch (kind) {
258 .tags => s.scopes.items[s.active_len - 1].tags.getPtr(name).?,
259 .vars => s.scopes.items[s.active_len - 1].vars.getPtr(name).?,
260 };
261}
262
263pub fn declareSymbol(
264 s: *SymbolStack,
265 p: *Parser,
266 name: StringId,
267 ty: Type,
268 tok: TokenIndex,
269 node: NodeIndex,
270) !void {
271 if (s.get(name, .vars)) |prev| {
272 switch (prev.kind) {
273 .enumeration => {
274 try p.errStr(.redefinition_different_sym, tok, p.tokSlice(tok));
275 try p.errTok(.previous_definition, prev.tok);
276 },
277 .decl => {
278 if (!ty.eql(prev.ty, p.comp, true)) {
279 try p.errStr(.redefinition_incompatible, tok, p.tokSlice(tok));
280 try p.errTok(.previous_definition, prev.tok);
281 }
282 },
283 .def, .constexpr => {
284 if (!ty.eql(prev.ty, p.comp, true)) {
285 try p.errStr(.redefinition_incompatible, tok, p.tokSlice(tok));
286 try p.errTok(.previous_definition, prev.tok);
287 } else {
288 return;
289 }
290 },
291 .typedef => {
292 try p.errStr(.redefinition_different_sym, tok, p.tokSlice(tok));
293 try p.errTok(.previous_definition, prev.tok);
294 },
295 else => unreachable,
296 }
297 }
298 try s.define(p.gpa, .{
299 .kind = .decl,
300 .name = name,
301 .tok = tok,
302 .ty = ty,
303 .node = node,
304 .val = .{},
305 });
306}
307
308pub fn defineParam(s: *SymbolStack, p: *Parser, name: StringId, ty: Type, tok: TokenIndex) !void {
309 if (s.get(name, .vars)) |prev| {
310 switch (prev.kind) {
311 .enumeration, .decl, .def, .constexpr => {
312 try p.errStr(.redefinition_of_parameter, tok, p.tokSlice(tok));
313 try p.errTok(.previous_definition, prev.tok);
314 },
315 .typedef => {
316 try p.errStr(.redefinition_different_sym, tok, p.tokSlice(tok));
317 try p.errTok(.previous_definition, prev.tok);
318 },
319 else => unreachable,
320 }
321 }
322 if (ty.is(.fp16) and !p.comp.hasHalfPrecisionFloatABI()) {
323 try p.errStr(.suggest_pointer_for_invalid_fp16, tok, "parameters");
324 }
325 try s.define(p.gpa, .{
326 .kind = .def,
327 .name = name,
328 .tok = tok,
329 .ty = ty,
330 .val = .{},
331 });
332}
333
334pub fn defineTag(
335 s: *SymbolStack,
336 p: *Parser,
337 name: StringId,
338 kind: Token.Id,
339 tok: TokenIndex,
340) !?Symbol {
341 const prev = s.get(name, .tags) orelse return null;
342 switch (prev.kind) {
343 .@"enum" => {
344 if (kind == .keyword_enum) return prev;
345 try p.errStr(.wrong_tag, tok, p.tokSlice(tok));
346 try p.errTok(.previous_definition, prev.tok);
347 return null;
348 },
349 .@"struct" => {
350 if (kind == .keyword_struct) return prev;
351 try p.errStr(.wrong_tag, tok, p.tokSlice(tok));
352 try p.errTok(.previous_definition, prev.tok);
353 return null;
354 },
355 .@"union" => {
356 if (kind == .keyword_union) return prev;
357 try p.errStr(.wrong_tag, tok, p.tokSlice(tok));
358 try p.errTok(.previous_definition, prev.tok);
359 return null;
360 },
361 else => unreachable,
362 }
363}
364
365pub fn defineEnumeration(
366 s: *SymbolStack,
367 p: *Parser,
368 name: StringId,
369 ty: Type,
370 tok: TokenIndex,
371 val: Value,
372) !void {
373 if (s.get(name, .vars)) |prev| {
374 switch (prev.kind) {
375 .enumeration => {
376 try p.errStr(.redefinition, tok, p.tokSlice(tok));
377 try p.errTok(.previous_definition, prev.tok);
378 return;
379 },
380 .decl, .def, .constexpr => {
381 try p.errStr(.redefinition_different_sym, tok, p.tokSlice(tok));
382 try p.errTok(.previous_definition, prev.tok);
383 return;
384 },
385 .typedef => {
386 try p.errStr(.redefinition_different_sym, tok, p.tokSlice(tok));
387 try p.errTok(.previous_definition, prev.tok);
388 },
389 else => unreachable,
390 }
391 }
392 try s.define(p.gpa, .{
393 .kind = .enumeration,
394 .name = name,
395 .tok = tok,
396 .ty = ty,
397 .val = val,
398 });
399}
lib/compiler/aro/aro/Tokenizer.zig deleted-2204
...@@ -1,2204 +0,0 @@
1const std = @import("std");
2const assert = std.debug.assert;
3const Compilation = @import("Compilation.zig");
4const Source = @import("Source.zig");
5const LangOpts = @import("LangOpts.zig");
6
7pub const Token = struct {
8 id: Id,
9 source: Source.Id,
10 start: u32 = 0,
11 end: u32 = 0,
12 line: u32 = 0,
13
14 pub const Id = enum(u8) {
15 invalid,
16 nl,
17 whitespace,
18 eof,
19 /// identifier containing solely basic character set characters
20 identifier,
21 /// identifier with at least one extended character
22 extended_identifier,
23
24 // string literals with prefixes
25 string_literal,
26 string_literal_utf_16,
27 string_literal_utf_8,
28 string_literal_utf_32,
29 string_literal_wide,
30
31 /// Any string literal with an embedded newline or EOF
32 /// Always a parser error; by default just a warning from preprocessor
33 unterminated_string_literal,
34
35 // <foobar> only generated by preprocessor
36 macro_string,
37
38 // char literals with prefixes
39 char_literal,
40 char_literal_utf_8,
41 char_literal_utf_16,
42 char_literal_utf_32,
43 char_literal_wide,
44
45 /// Any character literal with nothing inside the quotes
46 /// Always a parser error; by default just a warning from preprocessor
47 empty_char_literal,
48
49 /// Any character literal with an embedded newline or EOF
50 /// Always a parser error; by default just a warning from preprocessor
51 unterminated_char_literal,
52
53 /// `/* */` style comment without a closing `*/` before EOF
54 unterminated_comment,
55
56 /// Integer literal tokens generated by preprocessor.
57 one,
58 zero,
59
60 bang,
61 bang_equal,
62 pipe,
63 pipe_pipe,
64 pipe_equal,
65 equal,
66 equal_equal,
67 l_paren,
68 r_paren,
69 l_brace,
70 r_brace,
71 l_bracket,
72 r_bracket,
73 period,
74 ellipsis,
75 caret,
76 caret_equal,
77 plus,
78 plus_plus,
79 plus_equal,
80 minus,
81 minus_minus,
82 minus_equal,
83 asterisk,
84 asterisk_equal,
85 percent,
86 percent_equal,
87 arrow,
88 colon,
89 colon_colon,
90 semicolon,
91 slash,
92 slash_equal,
93 comma,
94 ampersand,
95 ampersand_ampersand,
96 ampersand_equal,
97 question_mark,
98 angle_bracket_left,
99 angle_bracket_left_equal,
100 angle_bracket_angle_bracket_left,
101 angle_bracket_angle_bracket_left_equal,
102 angle_bracket_right,
103 angle_bracket_right_equal,
104 angle_bracket_angle_bracket_right,
105 angle_bracket_angle_bracket_right_equal,
106 tilde,
107 hash,
108 hash_hash,
109
110 /// Special token to speed up preprocessing, `loc.end` will be an index to the param list.
111 macro_param,
112 /// Special token to signal that the argument must be replaced without expansion (e.g. in concatenation)
113 macro_param_no_expand,
114 /// Special token to speed up preprocessing, `loc.end` will be an index to the param list.
115 stringify_param,
116 /// Same as stringify_param, but for var args
117 stringify_va_args,
118 /// Special macro whitespace, always equal to a single space
119 macro_ws,
120 /// Special token for implementing __has_attribute
121 macro_param_has_attribute,
122 /// Special token for implementing __has_c_attribute
123 macro_param_has_c_attribute,
124 /// Special token for implementing __has_declspec_attribute
125 macro_param_has_declspec_attribute,
126 /// Special token for implementing __has_warning
127 macro_param_has_warning,
128 /// Special token for implementing __has_feature
129 macro_param_has_feature,
130 /// Special token for implementing __has_extension
131 macro_param_has_extension,
132 /// Special token for implementing __has_builtin
133 macro_param_has_builtin,
134 /// Special token for implementing __has_include
135 macro_param_has_include,
136 /// Special token for implementing __has_include_next
137 macro_param_has_include_next,
138 /// Special token for implementing __has_embed
139 macro_param_has_embed,
140 /// Special token for implementing __is_identifier
141 macro_param_is_identifier,
142 /// Special token for implementing __FILE__
143 macro_file,
144 /// Special token for implementing __LINE__
145 macro_line,
146 /// Special token for implementing __COUNTER__
147 macro_counter,
148 /// Special token for implementing _Pragma
149 macro_param_pragma_operator,
150
151 /// Special identifier for implementing __func__
152 macro_func,
153 /// Special identifier for implementing __FUNCTION__
154 macro_function,
155 /// Special identifier for implementing __PRETTY_FUNCTION__
156 macro_pretty_func,
157
158 keyword_auto,
159 keyword_auto_type,
160 keyword_break,
161 keyword_case,
162 keyword_char,
163 keyword_const,
164 keyword_continue,
165 keyword_default,
166 keyword_do,
167 keyword_double,
168 keyword_else,
169 keyword_enum,
170 keyword_extern,
171 keyword_float,
172 keyword_for,
173 keyword_goto,
174 keyword_if,
175 keyword_int,
176 keyword_long,
177 keyword_register,
178 keyword_return,
179 keyword_short,
180 keyword_signed,
181 keyword_signed1,
182 keyword_signed2,
183 keyword_sizeof,
184 keyword_static,
185 keyword_struct,
186 keyword_switch,
187 keyword_typedef,
188 keyword_typeof1,
189 keyword_typeof2,
190 keyword_union,
191 keyword_unsigned,
192 keyword_void,
193 keyword_volatile,
194 keyword_while,
195
196 // ISO C99
197 keyword_bool,
198 keyword_complex,
199 keyword_imaginary,
200 keyword_inline,
201 keyword_restrict,
202
203 // ISO C11
204 keyword_alignas,
205 keyword_alignof,
206 keyword_atomic,
207 keyword_generic,
208 keyword_noreturn,
209 keyword_static_assert,
210 keyword_thread_local,
211
212 // ISO C23
213 keyword_bit_int,
214 keyword_c23_alignas,
215 keyword_c23_alignof,
216 keyword_c23_bool,
217 keyword_c23_static_assert,
218 keyword_c23_thread_local,
219 keyword_constexpr,
220 keyword_true,
221 keyword_false,
222 keyword_nullptr,
223 keyword_typeof_unqual,
224
225 // Preprocessor directives
226 keyword_include,
227 keyword_include_next,
228 keyword_embed,
229 keyword_define,
230 keyword_defined,
231 keyword_undef,
232 keyword_ifdef,
233 keyword_ifndef,
234 keyword_elif,
235 keyword_elifdef,
236 keyword_elifndef,
237 keyword_endif,
238 keyword_error,
239 keyword_warning,
240 keyword_pragma,
241 keyword_line,
242 keyword_va_args,
243 keyword_va_opt,
244
245 // gcc keywords
246 keyword_const1,
247 keyword_const2,
248 keyword_inline1,
249 keyword_inline2,
250 keyword_volatile1,
251 keyword_volatile2,
252 keyword_restrict1,
253 keyword_restrict2,
254 keyword_alignof1,
255 keyword_alignof2,
256 keyword_typeof,
257 keyword_attribute1,
258 keyword_attribute2,
259 keyword_extension,
260 keyword_asm,
261 keyword_asm1,
262 keyword_asm2,
263 /// _Float128
264 keyword_float128_1,
265 /// __float128
266 keyword_float128_2,
267 keyword_int128,
268 keyword_imag1,
269 keyword_imag2,
270 keyword_real1,
271 keyword_real2,
272 keyword_float16,
273
274 // clang keywords
275 keyword_fp16,
276
277 // ms keywords
278 keyword_declspec,
279 keyword_int64,
280 keyword_int64_2,
281 keyword_int32,
282 keyword_int32_2,
283 keyword_int16,
284 keyword_int16_2,
285 keyword_int8,
286 keyword_int8_2,
287 keyword_stdcall,
288 keyword_stdcall2,
289 keyword_thiscall,
290 keyword_thiscall2,
291 keyword_vectorcall,
292 keyword_vectorcall2,
293
294 // builtins that require special parsing
295 builtin_choose_expr,
296 builtin_va_arg,
297 builtin_offsetof,
298 builtin_bitoffsetof,
299 builtin_types_compatible_p,
300
301 /// Generated by #embed directive
302 /// Decimal value with no prefix or suffix
303 embed_byte,
304
305 /// preprocessor number
306 /// An optional period, followed by a digit 0-9, followed by any number of letters
307 /// digits, underscores, periods, and exponents (e+, e-, E+, E-, p+, p-, P+, P-)
308 pp_num,
309
310 /// preprocessor placemarker token
311 /// generated if `##` is used with a zero-token argument
312 /// removed after substitution, so the parser should never see this
313 /// See C99 6.10.3.3.2
314 placemarker,
315
316 /// Virtual linemarker token output from preprocessor to indicate start of a new include
317 include_start,
318
319 /// Virtual linemarker token output from preprocessor to indicate resuming a file after
320 /// completion of the preceding #include
321 include_resume,
322
323 /// A comment token if asked to preserve comments.
324 comment,
325
326 /// Return true if token is identifier or keyword.
327 pub fn isMacroIdentifier(id: Id) bool {
328 switch (id) {
329 .keyword_include,
330 .keyword_include_next,
331 .keyword_embed,
332 .keyword_define,
333 .keyword_defined,
334 .keyword_undef,
335 .keyword_ifdef,
336 .keyword_ifndef,
337 .keyword_elif,
338 .keyword_elifdef,
339 .keyword_elifndef,
340 .keyword_endif,
341 .keyword_error,
342 .keyword_warning,
343 .keyword_pragma,
344 .keyword_line,
345 .keyword_va_args,
346 .keyword_va_opt,
347 .macro_func,
348 .macro_function,
349 .macro_pretty_func,
350 .keyword_auto,
351 .keyword_auto_type,
352 .keyword_break,
353 .keyword_case,
354 .keyword_char,
355 .keyword_const,
356 .keyword_continue,
357 .keyword_default,
358 .keyword_do,
359 .keyword_double,
360 .keyword_else,
361 .keyword_enum,
362 .keyword_extern,
363 .keyword_float,
364 .keyword_for,
365 .keyword_goto,
366 .keyword_if,
367 .keyword_int,
368 .keyword_long,
369 .keyword_register,
370 .keyword_return,
371 .keyword_short,
372 .keyword_signed,
373 .keyword_signed1,
374 .keyword_signed2,
375 .keyword_sizeof,
376 .keyword_static,
377 .keyword_struct,
378 .keyword_switch,
379 .keyword_typedef,
380 .keyword_union,
381 .keyword_unsigned,
382 .keyword_void,
383 .keyword_volatile,
384 .keyword_while,
385 .keyword_bool,
386 .keyword_complex,
387 .keyword_imaginary,
388 .keyword_inline,
389 .keyword_restrict,
390 .keyword_alignas,
391 .keyword_alignof,
392 .keyword_atomic,
393 .keyword_generic,
394 .keyword_noreturn,
395 .keyword_static_assert,
396 .keyword_thread_local,
397 .identifier,
398 .extended_identifier,
399 .keyword_typeof,
400 .keyword_typeof1,
401 .keyword_typeof2,
402 .keyword_const1,
403 .keyword_const2,
404 .keyword_inline1,
405 .keyword_inline2,
406 .keyword_volatile1,
407 .keyword_volatile2,
408 .keyword_restrict1,
409 .keyword_restrict2,
410 .keyword_alignof1,
411 .keyword_alignof2,
412 .builtin_choose_expr,
413 .builtin_va_arg,
414 .builtin_offsetof,
415 .builtin_bitoffsetof,
416 .builtin_types_compatible_p,
417 .keyword_attribute1,
418 .keyword_attribute2,
419 .keyword_extension,
420 .keyword_asm,
421 .keyword_asm1,
422 .keyword_asm2,
423 .keyword_float128_1,
424 .keyword_float128_2,
425 .keyword_int128,
426 .keyword_imag1,
427 .keyword_imag2,
428 .keyword_real1,
429 .keyword_real2,
430 .keyword_float16,
431 .keyword_fp16,
432 .keyword_declspec,
433 .keyword_int64,
434 .keyword_int64_2,
435 .keyword_int32,
436 .keyword_int32_2,
437 .keyword_int16,
438 .keyword_int16_2,
439 .keyword_int8,
440 .keyword_int8_2,
441 .keyword_stdcall,
442 .keyword_stdcall2,
443 .keyword_thiscall,
444 .keyword_thiscall2,
445 .keyword_vectorcall,
446 .keyword_vectorcall2,
447 .keyword_bit_int,
448 .keyword_c23_alignas,
449 .keyword_c23_alignof,
450 .keyword_c23_bool,
451 .keyword_c23_static_assert,
452 .keyword_c23_thread_local,
453 .keyword_constexpr,
454 .keyword_true,
455 .keyword_false,
456 .keyword_nullptr,
457 .keyword_typeof_unqual,
458 => return true,
459 else => return false,
460 }
461 }
462
463 /// Turn macro keywords into identifiers.
464 /// `keyword_defined` is special since it should only turn into an identifier if
465 /// we are *not* in an #if or #elif expression
466 pub fn simplifyMacroKeywordExtra(id: *Id, defined_to_identifier: bool) void {
467 switch (id.*) {
468 .keyword_include,
469 .keyword_include_next,
470 .keyword_embed,
471 .keyword_define,
472 .keyword_undef,
473 .keyword_ifdef,
474 .keyword_ifndef,
475 .keyword_elif,
476 .keyword_elifdef,
477 .keyword_elifndef,
478 .keyword_endif,
479 .keyword_error,
480 .keyword_warning,
481 .keyword_pragma,
482 .keyword_line,
483 .keyword_va_args,
484 .keyword_va_opt,
485 => id.* = .identifier,
486 .keyword_defined => if (defined_to_identifier) {
487 id.* = .identifier;
488 },
489 else => {},
490 }
491 }
492
493 pub fn simplifyMacroKeyword(id: *Id) void {
494 simplifyMacroKeywordExtra(id, false);
495 }
496
497 pub fn lexeme(id: Id) ?[]const u8 {
498 return switch (id) {
499 .include_start,
500 .include_resume,
501 => unreachable,
502
503 .unterminated_comment,
504 .invalid,
505 .identifier,
506 .extended_identifier,
507 .string_literal,
508 .string_literal_utf_16,
509 .string_literal_utf_8,
510 .string_literal_utf_32,
511 .string_literal_wide,
512 .unterminated_string_literal,
513 .unterminated_char_literal,
514 .empty_char_literal,
515 .char_literal,
516 .char_literal_utf_8,
517 .char_literal_utf_16,
518 .char_literal_utf_32,
519 .char_literal_wide,
520 .macro_string,
521 .whitespace,
522 .pp_num,
523 .embed_byte,
524 .comment,
525 => null,
526
527 .zero => "0",
528 .one => "1",
529
530 .nl,
531 .eof,
532 .macro_param,
533 .macro_param_no_expand,
534 .stringify_param,
535 .stringify_va_args,
536 .macro_param_has_attribute,
537 .macro_param_has_c_attribute,
538 .macro_param_has_declspec_attribute,
539 .macro_param_has_warning,
540 .macro_param_has_feature,
541 .macro_param_has_extension,
542 .macro_param_has_builtin,
543 .macro_param_has_include,
544 .macro_param_has_include_next,
545 .macro_param_has_embed,
546 .macro_param_is_identifier,
547 .macro_file,
548 .macro_line,
549 .macro_counter,
550 .macro_param_pragma_operator,
551 .placemarker,
552 => "",
553 .macro_ws => " ",
554
555 .macro_func => "__func__",
556 .macro_function => "__FUNCTION__",
557 .macro_pretty_func => "__PRETTY_FUNCTION__",
558
559 .bang => "!",
560 .bang_equal => "!=",
561 .pipe => "|",
562 .pipe_pipe => "||",
563 .pipe_equal => "|=",
564 .equal => "=",
565 .equal_equal => "==",
566 .l_paren => "(",
567 .r_paren => ")",
568 .l_brace => "{",
569 .r_brace => "}",
570 .l_bracket => "[",
571 .r_bracket => "]",
572 .period => ".",
573 .ellipsis => "...",
574 .caret => "^",
575 .caret_equal => "^=",
576 .plus => "+",
577 .plus_plus => "++",
578 .plus_equal => "+=",
579 .minus => "-",
580 .minus_minus => "--",
581 .minus_equal => "-=",
582 .asterisk => "*",
583 .asterisk_equal => "*=",
584 .percent => "%",
585 .percent_equal => "%=",
586 .arrow => "->",
587 .colon => ":",
588 .colon_colon => "::",
589 .semicolon => ";",
590 .slash => "/",
591 .slash_equal => "/=",
592 .comma => ",",
593 .ampersand => "&",
594 .ampersand_ampersand => "&&",
595 .ampersand_equal => "&=",
596 .question_mark => "?",
597 .angle_bracket_left => "<",
598 .angle_bracket_left_equal => "<=",
599 .angle_bracket_angle_bracket_left => "<<",
600 .angle_bracket_angle_bracket_left_equal => "<<=",
601 .angle_bracket_right => ">",
602 .angle_bracket_right_equal => ">=",
603 .angle_bracket_angle_bracket_right => ">>",
604 .angle_bracket_angle_bracket_right_equal => ">>=",
605 .tilde => "~",
606 .hash => "#",
607 .hash_hash => "##",
608
609 .keyword_auto => "auto",
610 .keyword_auto_type => "__auto_type",
611 .keyword_break => "break",
612 .keyword_case => "case",
613 .keyword_char => "char",
614 .keyword_const => "const",
615 .keyword_continue => "continue",
616 .keyword_default => "default",
617 .keyword_do => "do",
618 .keyword_double => "double",
619 .keyword_else => "else",
620 .keyword_enum => "enum",
621 .keyword_extern => "extern",
622 .keyword_float => "float",
623 .keyword_for => "for",
624 .keyword_goto => "goto",
625 .keyword_if => "if",
626 .keyword_int => "int",
627 .keyword_long => "long",
628 .keyword_register => "register",
629 .keyword_return => "return",
630 .keyword_short => "short",
631 .keyword_signed => "signed",
632 .keyword_signed1 => "__signed",
633 .keyword_signed2 => "__signed__",
634 .keyword_sizeof => "sizeof",
635 .keyword_static => "static",
636 .keyword_struct => "struct",
637 .keyword_switch => "switch",
638 .keyword_typedef => "typedef",
639 .keyword_typeof => "typeof",
640 .keyword_union => "union",
641 .keyword_unsigned => "unsigned",
642 .keyword_void => "void",
643 .keyword_volatile => "volatile",
644 .keyword_while => "while",
645 .keyword_bool => "_Bool",
646 .keyword_complex => "_Complex",
647 .keyword_imaginary => "_Imaginary",
648 .keyword_inline => "inline",
649 .keyword_restrict => "restrict",
650 .keyword_alignas => "_Alignas",
651 .keyword_alignof => "_Alignof",
652 .keyword_atomic => "_Atomic",
653 .keyword_generic => "_Generic",
654 .keyword_noreturn => "_Noreturn",
655 .keyword_static_assert => "_Static_assert",
656 .keyword_thread_local => "_Thread_local",
657 .keyword_bit_int => "_BitInt",
658 .keyword_c23_alignas => "alignas",
659 .keyword_c23_alignof => "alignof",
660 .keyword_c23_bool => "bool",
661 .keyword_c23_static_assert => "static_assert",
662 .keyword_c23_thread_local => "thread_local",
663 .keyword_constexpr => "constexpr",
664 .keyword_true => "true",
665 .keyword_false => "false",
666 .keyword_nullptr => "nullptr",
667 .keyword_typeof_unqual => "typeof_unqual",
668 .keyword_include => "include",
669 .keyword_include_next => "include_next",
670 .keyword_embed => "embed",
671 .keyword_define => "define",
672 .keyword_defined => "defined",
673 .keyword_undef => "undef",
674 .keyword_ifdef => "ifdef",
675 .keyword_ifndef => "ifndef",
676 .keyword_elif => "elif",
677 .keyword_elifdef => "elifdef",
678 .keyword_elifndef => "elifndef",
679 .keyword_endif => "endif",
680 .keyword_error => "error",
681 .keyword_warning => "warning",
682 .keyword_pragma => "pragma",
683 .keyword_line => "line",
684 .keyword_va_args => "__VA_ARGS__",
685 .keyword_va_opt => "__VA_OPT__",
686 .keyword_const1 => "__const",
687 .keyword_const2 => "__const__",
688 .keyword_inline1 => "__inline",
689 .keyword_inline2 => "__inline__",
690 .keyword_volatile1 => "__volatile",
691 .keyword_volatile2 => "__volatile__",
692 .keyword_restrict1 => "__restrict",
693 .keyword_restrict2 => "__restrict__",
694 .keyword_alignof1 => "__alignof",
695 .keyword_alignof2 => "__alignof__",
696 .keyword_typeof1 => "__typeof",
697 .keyword_typeof2 => "__typeof__",
698 .builtin_choose_expr => "__builtin_choose_expr",
699 .builtin_va_arg => "__builtin_va_arg",
700 .builtin_offsetof => "__builtin_offsetof",
701 .builtin_bitoffsetof => "__builtin_bitoffsetof",
702 .builtin_types_compatible_p => "__builtin_types_compatible_p",
703 .keyword_attribute1 => "__attribute",
704 .keyword_attribute2 => "__attribute__",
705 .keyword_extension => "__extension__",
706 .keyword_asm => "asm",
707 .keyword_asm1 => "__asm",
708 .keyword_asm2 => "__asm__",
709 .keyword_float128_1 => "_Float128",
710 .keyword_float128_2 => "__float128",
711 .keyword_int128 => "__int128",
712 .keyword_imag1 => "__imag",
713 .keyword_imag2 => "__imag__",
714 .keyword_real1 => "__real",
715 .keyword_real2 => "__real__",
716 .keyword_float16 => "_Float16",
717 .keyword_fp16 => "__fp16",
718 .keyword_declspec => "__declspec",
719 .keyword_int64 => "__int64",
720 .keyword_int64_2 => "_int64",
721 .keyword_int32 => "__int32",
722 .keyword_int32_2 => "_int32",
723 .keyword_int16 => "__int16",
724 .keyword_int16_2 => "_int16",
725 .keyword_int8 => "__int8",
726 .keyword_int8_2 => "_int8",
727 .keyword_stdcall => "__stdcall",
728 .keyword_stdcall2 => "_stdcall",
729 .keyword_thiscall => "__thiscall",
730 .keyword_thiscall2 => "_thiscall",
731 .keyword_vectorcall => "__vectorcall",
732 .keyword_vectorcall2 => "_vectorcall",
733 };
734 }
735
736 pub fn symbol(id: Id) []const u8 {
737 return switch (id) {
738 .macro_string => unreachable,
739 .invalid => "invalid bytes",
740 .identifier,
741 .extended_identifier,
742 .macro_func,
743 .macro_function,
744 .macro_pretty_func,
745 .builtin_choose_expr,
746 .builtin_va_arg,
747 .builtin_offsetof,
748 .builtin_bitoffsetof,
749 .builtin_types_compatible_p,
750 => "an identifier",
751 .string_literal,
752 .string_literal_utf_16,
753 .string_literal_utf_8,
754 .string_literal_utf_32,
755 .string_literal_wide,
756 .unterminated_string_literal,
757 => "a string literal",
758 .char_literal,
759 .char_literal_utf_8,
760 .char_literal_utf_16,
761 .char_literal_utf_32,
762 .char_literal_wide,
763 .unterminated_char_literal,
764 .empty_char_literal,
765 => "a character literal",
766 .pp_num, .embed_byte => "A number",
767 else => id.lexeme().?,
768 };
769 }
770
771 /// tokens that can start an expression parsed by Preprocessor.expr
772 /// Note that eof, r_paren, and string literals cannot actually start a
773 /// preprocessor expression, but we include them here so that a nicer
774 /// error message can be generated by the parser.
775 pub fn validPreprocessorExprStart(id: Id) bool {
776 return switch (id) {
777 .eof,
778 .r_paren,
779 .string_literal,
780 .string_literal_utf_16,
781 .string_literal_utf_8,
782 .string_literal_utf_32,
783 .string_literal_wide,
784
785 .char_literal,
786 .char_literal_utf_8,
787 .char_literal_utf_16,
788 .char_literal_utf_32,
789 .char_literal_wide,
790 .l_paren,
791 .plus,
792 .minus,
793 .tilde,
794 .bang,
795 .identifier,
796 .extended_identifier,
797 .keyword_defined,
798 .one,
799 .zero,
800 .pp_num,
801 .keyword_true,
802 .keyword_false,
803 => true,
804 else => false,
805 };
806 }
807
808 pub fn allowsDigraphs(id: Id, langopts: LangOpts) bool {
809 return switch (id) {
810 .l_bracket,
811 .r_bracket,
812 .l_brace,
813 .r_brace,
814 .hash,
815 .hash_hash,
816 => langopts.hasDigraphs(),
817 else => false,
818 };
819 }
820
821 pub fn canOpenGCCAsmStmt(id: Id) bool {
822 return switch (id) {
823 .keyword_volatile, .keyword_volatile1, .keyword_volatile2, .keyword_inline, .keyword_inline1, .keyword_inline2, .keyword_goto, .l_paren => true,
824 else => false,
825 };
826 }
827
828 pub fn isStringLiteral(id: Id) bool {
829 return switch (id) {
830 .string_literal, .string_literal_utf_16, .string_literal_utf_8, .string_literal_utf_32, .string_literal_wide => true,
831 else => false,
832 };
833 }
834 };
835
836 /// double underscore and underscore + capital letter identifiers
837 /// belong to the implementation namespace, so we always convert them
838 /// to keywords.
839 pub fn getTokenId(langopts: LangOpts, str: []const u8) Token.Id {
840 const kw = all_kws.get(str) orelse return .identifier;
841 const standard = langopts.standard;
842 return switch (kw) {
843 .keyword_inline => if (standard.isGNU() or standard.atLeast(.c99)) kw else .identifier,
844 .keyword_restrict => if (standard.atLeast(.c99)) kw else .identifier,
845 .keyword_typeof => if (standard.isGNU() or standard.atLeast(.c23)) kw else .identifier,
846 .keyword_asm => if (standard.isGNU()) kw else .identifier,
847 .keyword_declspec => if (langopts.declspec_attrs) kw else .identifier,
848
849 .keyword_c23_alignas,
850 .keyword_c23_alignof,
851 .keyword_c23_bool,
852 .keyword_c23_static_assert,
853 .keyword_c23_thread_local,
854 .keyword_constexpr,
855 .keyword_true,
856 .keyword_false,
857 .keyword_nullptr,
858 .keyword_typeof_unqual,
859 .keyword_elifdef,
860 .keyword_elifndef,
861 => if (standard.atLeast(.c23)) kw else .identifier,
862
863 .keyword_int64,
864 .keyword_int64_2,
865 .keyword_int32,
866 .keyword_int32_2,
867 .keyword_int16,
868 .keyword_int16_2,
869 .keyword_int8,
870 .keyword_int8_2,
871 .keyword_stdcall2,
872 .keyword_thiscall2,
873 .keyword_vectorcall2,
874 => if (langopts.ms_extensions) kw else .identifier,
875 else => kw,
876 };
877 }
878
879 const all_kws = std.StaticStringMap(Id).initComptime(.{
880 .{ "auto", .keyword_auto },
881 .{ "break", .keyword_break },
882 .{ "case", .keyword_case },
883 .{ "char", .keyword_char },
884 .{ "const", .keyword_const },
885 .{ "continue", .keyword_continue },
886 .{ "default", .keyword_default },
887 .{ "do", .keyword_do },
888 .{ "double", .keyword_double },
889 .{ "else", .keyword_else },
890 .{ "enum", .keyword_enum },
891 .{ "extern", .keyword_extern },
892 .{ "float", .keyword_float },
893 .{ "for", .keyword_for },
894 .{ "goto", .keyword_goto },
895 .{ "if", .keyword_if },
896 .{ "int", .keyword_int },
897 .{ "long", .keyword_long },
898 .{ "register", .keyword_register },
899 .{ "return", .keyword_return },
900 .{ "short", .keyword_short },
901 .{ "signed", .keyword_signed },
902 .{ "__signed", .keyword_signed1 },
903 .{ "__signed__", .keyword_signed2 },
904 .{ "sizeof", .keyword_sizeof },
905 .{ "static", .keyword_static },
906 .{ "struct", .keyword_struct },
907 .{ "switch", .keyword_switch },
908 .{ "typedef", .keyword_typedef },
909 .{ "union", .keyword_union },
910 .{ "unsigned", .keyword_unsigned },
911 .{ "void", .keyword_void },
912 .{ "volatile", .keyword_volatile },
913 .{ "while", .keyword_while },
914 .{ "__typeof__", .keyword_typeof2 },
915 .{ "__typeof", .keyword_typeof1 },
916
917 // ISO C99
918 .{ "_Bool", .keyword_bool },
919 .{ "_Complex", .keyword_complex },
920 .{ "_Imaginary", .keyword_imaginary },
921 .{ "inline", .keyword_inline },
922 .{ "restrict", .keyword_restrict },
923
924 // ISO C11
925 .{ "_Alignas", .keyword_alignas },
926 .{ "_Alignof", .keyword_alignof },
927 .{ "_Atomic", .keyword_atomic },
928 .{ "_Generic", .keyword_generic },
929 .{ "_Noreturn", .keyword_noreturn },
930 .{ "_Static_assert", .keyword_static_assert },
931 .{ "_Thread_local", .keyword_thread_local },
932
933 // ISO C23
934 .{ "_BitInt", .keyword_bit_int },
935 .{ "alignas", .keyword_c23_alignas },
936 .{ "alignof", .keyword_c23_alignof },
937 .{ "bool", .keyword_c23_bool },
938 .{ "static_assert", .keyword_c23_static_assert },
939 .{ "thread_local", .keyword_c23_thread_local },
940 .{ "constexpr", .keyword_constexpr },
941 .{ "true", .keyword_true },
942 .{ "false", .keyword_false },
943 .{ "nullptr", .keyword_nullptr },
944 .{ "typeof_unqual", .keyword_typeof_unqual },
945
946 // Preprocessor directives
947 .{ "include", .keyword_include },
948 .{ "include_next", .keyword_include_next },
949 .{ "embed", .keyword_embed },
950 .{ "define", .keyword_define },
951 .{ "defined", .keyword_defined },
952 .{ "undef", .keyword_undef },
953 .{ "ifdef", .keyword_ifdef },
954 .{ "ifndef", .keyword_ifndef },
955 .{ "elif", .keyword_elif },
956 .{ "elifdef", .keyword_elifdef },
957 .{ "elifndef", .keyword_elifndef },
958 .{ "endif", .keyword_endif },
959 .{ "error", .keyword_error },
960 .{ "warning", .keyword_warning },
961 .{ "pragma", .keyword_pragma },
962 .{ "line", .keyword_line },
963 .{ "__VA_ARGS__", .keyword_va_args },
964 .{ "__VA_OPT__", .keyword_va_opt },
965 .{ "__func__", .macro_func },
966 .{ "__FUNCTION__", .macro_function },
967 .{ "__PRETTY_FUNCTION__", .macro_pretty_func },
968
969 // gcc keywords
970 .{ "__auto_type", .keyword_auto_type },
971 .{ "__const", .keyword_const1 },
972 .{ "__const__", .keyword_const2 },
973 .{ "__inline", .keyword_inline1 },
974 .{ "__inline__", .keyword_inline2 },
975 .{ "__volatile", .keyword_volatile1 },
976 .{ "__volatile__", .keyword_volatile2 },
977 .{ "__restrict", .keyword_restrict1 },
978 .{ "__restrict__", .keyword_restrict2 },
979 .{ "__alignof", .keyword_alignof1 },
980 .{ "__alignof__", .keyword_alignof2 },
981 .{ "typeof", .keyword_typeof },
982 .{ "__attribute", .keyword_attribute1 },
983 .{ "__attribute__", .keyword_attribute2 },
984 .{ "__extension__", .keyword_extension },
985 .{ "asm", .keyword_asm },
986 .{ "__asm", .keyword_asm1 },
987 .{ "__asm__", .keyword_asm2 },
988 .{ "_Float128", .keyword_float128_1 },
989 .{ "__float128", .keyword_float128_2 },
990 .{ "__int128", .keyword_int128 },
991 .{ "__imag", .keyword_imag1 },
992 .{ "__imag__", .keyword_imag2 },
993 .{ "__real", .keyword_real1 },
994 .{ "__real__", .keyword_real2 },
995 .{ "_Float16", .keyword_float16 },
996
997 // clang keywords
998 .{ "__fp16", .keyword_fp16 },
999
1000 // ms keywords
1001 .{ "__declspec", .keyword_declspec },
1002 .{ "__int64", .keyword_int64 },
1003 .{ "_int64", .keyword_int64_2 },
1004 .{ "__int32", .keyword_int32 },
1005 .{ "_int32", .keyword_int32_2 },
1006 .{ "__int16", .keyword_int16 },
1007 .{ "_int16", .keyword_int16_2 },
1008 .{ "__int8", .keyword_int8 },
1009 .{ "_int8", .keyword_int8_2 },
1010 .{ "__stdcall", .keyword_stdcall },
1011 .{ "_stdcall", .keyword_stdcall2 },
1012 .{ "__thiscall", .keyword_thiscall },
1013 .{ "_thiscall", .keyword_thiscall2 },
1014 .{ "__vectorcall", .keyword_vectorcall },
1015 .{ "_vectorcall", .keyword_vectorcall2 },
1016
1017 // builtins that require special parsing
1018 .{ "__builtin_choose_expr", .builtin_choose_expr },
1019 .{ "__builtin_va_arg", .builtin_va_arg },
1020 .{ "__builtin_offsetof", .builtin_offsetof },
1021 .{ "__builtin_bitoffsetof", .builtin_bitoffsetof },
1022 .{ "__builtin_types_compatible_p", .builtin_types_compatible_p },
1023 });
1024};
1025
1026const Tokenizer = @This();
1027
1028buf: []const u8,
1029index: u32 = 0,
1030source: Source.Id,
1031langopts: LangOpts,
1032line: u32 = 1,
1033
1034pub fn next(self: *Tokenizer) Token {
1035 var state: enum {
1036 start,
1037 whitespace,
1038 u,
1039 u8,
1040 U,
1041 L,
1042 string_literal,
1043 char_literal_start,
1044 char_literal,
1045 char_escape_sequence,
1046 string_escape_sequence,
1047 identifier,
1048 extended_identifier,
1049 equal,
1050 bang,
1051 pipe,
1052 colon,
1053 percent,
1054 asterisk,
1055 plus,
1056 angle_bracket_left,
1057 angle_bracket_angle_bracket_left,
1058 angle_bracket_right,
1059 angle_bracket_angle_bracket_right,
1060 caret,
1061 period,
1062 period2,
1063 minus,
1064 slash,
1065 ampersand,
1066 hash,
1067 hash_digraph,
1068 hash_hash_digraph_partial,
1069 line_comment,
1070 multi_line_comment,
1071 multi_line_comment_asterisk,
1072 multi_line_comment_done,
1073 pp_num,
1074 pp_num_exponent,
1075 pp_num_digit_separator,
1076 } = .start;
1077
1078 var start = self.index;
1079 var id: Token.Id = .eof;
1080
1081 while (self.index < self.buf.len) : (self.index += 1) {
1082 const c = self.buf[self.index];
1083 switch (state) {
1084 .start => switch (c) {
1085 '\n' => {
1086 id = .nl;
1087 self.index += 1;
1088 self.line += 1;
1089 break;
1090 },
1091 '"' => {
1092 id = .string_literal;
1093 state = .string_literal;
1094 },
1095 '\'' => {
1096 id = .char_literal;
1097 state = .char_literal_start;
1098 },
1099 'u' => state = .u,
1100 'U' => state = .U,
1101 'L' => state = .L,
1102 'a'...'t', 'v'...'z', 'A'...'K', 'M'...'T', 'V'...'Z', '_' => state = .identifier,
1103 '=' => state = .equal,
1104 '!' => state = .bang,
1105 '|' => state = .pipe,
1106 '(' => {
1107 id = .l_paren;
1108 self.index += 1;
1109 break;
1110 },
1111 ')' => {
1112 id = .r_paren;
1113 self.index += 1;
1114 break;
1115 },
1116 '[' => {
1117 id = .l_bracket;
1118 self.index += 1;
1119 break;
1120 },
1121 ']' => {
1122 id = .r_bracket;
1123 self.index += 1;
1124 break;
1125 },
1126 ';' => {
1127 id = .semicolon;
1128 self.index += 1;
1129 break;
1130 },
1131 ',' => {
1132 id = .comma;
1133 self.index += 1;
1134 break;
1135 },
1136 '?' => {
1137 id = .question_mark;
1138 self.index += 1;
1139 break;
1140 },
1141 ':' => state = .colon,
1142 '%' => state = .percent,
1143 '*' => state = .asterisk,
1144 '+' => state = .plus,
1145 '<' => state = .angle_bracket_left,
1146 '>' => state = .angle_bracket_right,
1147 '^' => state = .caret,
1148 '{' => {
1149 id = .l_brace;
1150 self.index += 1;
1151 break;
1152 },
1153 '}' => {
1154 id = .r_brace;
1155 self.index += 1;
1156 break;
1157 },
1158 '~' => {
1159 id = .tilde;
1160 self.index += 1;
1161 break;
1162 },
1163 '.' => state = .period,
1164 '-' => state = .minus,
1165 '/' => state = .slash,
1166 '&' => state = .ampersand,
1167 '#' => state = .hash,
1168 '0'...'9' => state = .pp_num,
1169 '\t', '\x0B', '\x0C', ' ' => state = .whitespace,
1170 '$' => if (self.langopts.dollars_in_identifiers) {
1171 state = .extended_identifier;
1172 } else {
1173 id = .invalid;
1174 self.index += 1;
1175 break;
1176 },
1177 0x1A => if (self.langopts.ms_extensions) {
1178 id = .eof;
1179 break;
1180 } else {
1181 id = .invalid;
1182 self.index += 1;
1183 break;
1184 },
1185 0x80...0xFF => state = .extended_identifier,
1186 else => {
1187 id = .invalid;
1188 self.index += 1;
1189 break;
1190 },
1191 },
1192 .whitespace => switch (c) {
1193 '\t', '\x0B', '\x0C', ' ' => {},
1194 else => {
1195 id = .whitespace;
1196 break;
1197 },
1198 },
1199 .u => switch (c) {
1200 '8' => {
1201 state = .u8;
1202 },
1203 '\'' => {
1204 id = .char_literal_utf_16;
1205 state = .char_literal_start;
1206 },
1207 '\"' => {
1208 id = .string_literal_utf_16;
1209 state = .string_literal;
1210 },
1211 else => {
1212 self.index -= 1;
1213 state = .identifier;
1214 },
1215 },
1216 .u8 => switch (c) {
1217 '\"' => {
1218 id = .string_literal_utf_8;
1219 state = .string_literal;
1220 },
1221 '\'' => {
1222 id = .char_literal_utf_8;
1223 state = .char_literal_start;
1224 },
1225 else => {
1226 self.index -= 1;
1227 state = .identifier;
1228 },
1229 },
1230 .U => switch (c) {
1231 '\'' => {
1232 id = .char_literal_utf_32;
1233 state = .char_literal_start;
1234 },
1235 '\"' => {
1236 id = .string_literal_utf_32;
1237 state = .string_literal;
1238 },
1239 else => {
1240 self.index -= 1;
1241 state = .identifier;
1242 },
1243 },
1244 .L => switch (c) {
1245 '\'' => {
1246 id = .char_literal_wide;
1247 state = .char_literal_start;
1248 },
1249 '\"' => {
1250 id = .string_literal_wide;
1251 state = .string_literal;
1252 },
1253 else => {
1254 self.index -= 1;
1255 state = .identifier;
1256 },
1257 },
1258 .string_literal => switch (c) {
1259 '\\' => {
1260 state = .string_escape_sequence;
1261 },
1262 '"' => {
1263 self.index += 1;
1264 break;
1265 },
1266 '\n' => {
1267 id = .unterminated_string_literal;
1268 break;
1269 },
1270 '\r' => unreachable,
1271 else => {},
1272 },
1273 .char_literal_start => switch (c) {
1274 '\\' => {
1275 state = .char_escape_sequence;
1276 },
1277 '\'' => {
1278 id = .empty_char_literal;
1279 self.index += 1;
1280 break;
1281 },
1282 '\n' => {
1283 id = .unterminated_char_literal;
1284 break;
1285 },
1286 else => {
1287 state = .char_literal;
1288 },
1289 },
1290 .char_literal => switch (c) {
1291 '\\' => {
1292 state = .char_escape_sequence;
1293 },
1294 '\'' => {
1295 self.index += 1;
1296 break;
1297 },
1298 '\n' => {
1299 id = .unterminated_char_literal;
1300 break;
1301 },
1302 else => {},
1303 },
1304 .char_escape_sequence => switch (c) {
1305 '\r', '\n' => {
1306 id = .unterminated_char_literal;
1307 break;
1308 },
1309 else => state = .char_literal,
1310 },
1311 .string_escape_sequence => switch (c) {
1312 '\r', '\n' => {
1313 id = .unterminated_string_literal;
1314 break;
1315 },
1316 else => state = .string_literal,
1317 },
1318 .identifier, .extended_identifier => switch (c) {
1319 'a'...'z', 'A'...'Z', '_', '0'...'9' => {},
1320 '$' => if (self.langopts.dollars_in_identifiers) {
1321 state = .extended_identifier;
1322 } else {
1323 id = if (state == .identifier) Token.getTokenId(self.langopts, self.buf[start..self.index]) else .extended_identifier;
1324 break;
1325 },
1326 0x80...0xFF => state = .extended_identifier,
1327 else => {
1328 id = if (state == .identifier) Token.getTokenId(self.langopts, self.buf[start..self.index]) else .extended_identifier;
1329 break;
1330 },
1331 },
1332 .equal => switch (c) {
1333 '=' => {
1334 id = .equal_equal;
1335 self.index += 1;
1336 break;
1337 },
1338 else => {
1339 id = .equal;
1340 break;
1341 },
1342 },
1343 .bang => switch (c) {
1344 '=' => {
1345 id = .bang_equal;
1346 self.index += 1;
1347 break;
1348 },
1349 else => {
1350 id = .bang;
1351 break;
1352 },
1353 },
1354 .pipe => switch (c) {
1355 '=' => {
1356 id = .pipe_equal;
1357 self.index += 1;
1358 break;
1359 },
1360 '|' => {
1361 id = .pipe_pipe;
1362 self.index += 1;
1363 break;
1364 },
1365 else => {
1366 id = .pipe;
1367 break;
1368 },
1369 },
1370 .colon => switch (c) {
1371 '>' => {
1372 if (self.langopts.hasDigraphs()) {
1373 id = .r_bracket;
1374 self.index += 1;
1375 } else {
1376 id = .colon;
1377 }
1378 break;
1379 },
1380 ':' => {
1381 if (self.langopts.standard.atLeast(.c23)) {
1382 id = .colon_colon;
1383 self.index += 1;
1384 break;
1385 } else {
1386 id = .colon;
1387 break;
1388 }
1389 },
1390 else => {
1391 id = .colon;
1392 break;
1393 },
1394 },
1395 .percent => switch (c) {
1396 '=' => {
1397 id = .percent_equal;
1398 self.index += 1;
1399 break;
1400 },
1401 '>' => {
1402 if (self.langopts.hasDigraphs()) {
1403 id = .r_brace;
1404 self.index += 1;
1405 } else {
1406 id = .percent;
1407 }
1408 break;
1409 },
1410 ':' => {
1411 if (self.langopts.hasDigraphs()) {
1412 state = .hash_digraph;
1413 } else {
1414 id = .percent;
1415 break;
1416 }
1417 },
1418 else => {
1419 id = .percent;
1420 break;
1421 },
1422 },
1423 .asterisk => switch (c) {
1424 '=' => {
1425 id = .asterisk_equal;
1426 self.index += 1;
1427 break;
1428 },
1429 else => {
1430 id = .asterisk;
1431 break;
1432 },
1433 },
1434 .plus => switch (c) {
1435 '=' => {
1436 id = .plus_equal;
1437 self.index += 1;
1438 break;
1439 },
1440 '+' => {
1441 id = .plus_plus;
1442 self.index += 1;
1443 break;
1444 },
1445 else => {
1446 id = .plus;
1447 break;
1448 },
1449 },
1450 .angle_bracket_left => switch (c) {
1451 '<' => state = .angle_bracket_angle_bracket_left,
1452 '=' => {
1453 id = .angle_bracket_left_equal;
1454 self.index += 1;
1455 break;
1456 },
1457 ':' => {
1458 if (self.langopts.hasDigraphs()) {
1459 id = .l_bracket;
1460 self.index += 1;
1461 } else {
1462 id = .angle_bracket_left;
1463 }
1464 break;
1465 },
1466 '%' => {
1467 if (self.langopts.hasDigraphs()) {
1468 id = .l_brace;
1469 self.index += 1;
1470 } else {
1471 id = .angle_bracket_left;
1472 }
1473 break;
1474 },
1475 else => {
1476 id = .angle_bracket_left;
1477 break;
1478 },
1479 },
1480 .angle_bracket_angle_bracket_left => switch (c) {
1481 '=' => {
1482 id = .angle_bracket_angle_bracket_left_equal;
1483 self.index += 1;
1484 break;
1485 },
1486 else => {
1487 id = .angle_bracket_angle_bracket_left;
1488 break;
1489 },
1490 },
1491 .angle_bracket_right => switch (c) {
1492 '>' => state = .angle_bracket_angle_bracket_right,
1493 '=' => {
1494 id = .angle_bracket_right_equal;
1495 self.index += 1;
1496 break;
1497 },
1498 else => {
1499 id = .angle_bracket_right;
1500 break;
1501 },
1502 },
1503 .angle_bracket_angle_bracket_right => switch (c) {
1504 '=' => {
1505 id = .angle_bracket_angle_bracket_right_equal;
1506 self.index += 1;
1507 break;
1508 },
1509 else => {
1510 id = .angle_bracket_angle_bracket_right;
1511 break;
1512 },
1513 },
1514 .caret => switch (c) {
1515 '=' => {
1516 id = .caret_equal;
1517 self.index += 1;
1518 break;
1519 },
1520 else => {
1521 id = .caret;
1522 break;
1523 },
1524 },
1525 .period => switch (c) {
1526 '.' => state = .period2,
1527 '0'...'9' => state = .pp_num,
1528 else => {
1529 id = .period;
1530 break;
1531 },
1532 },
1533 .period2 => switch (c) {
1534 '.' => {
1535 id = .ellipsis;
1536 self.index += 1;
1537 break;
1538 },
1539 else => {
1540 id = .period;
1541 self.index -= 1;
1542 break;
1543 },
1544 },
1545 .minus => switch (c) {
1546 '>' => {
1547 id = .arrow;
1548 self.index += 1;
1549 break;
1550 },
1551 '=' => {
1552 id = .minus_equal;
1553 self.index += 1;
1554 break;
1555 },
1556 '-' => {
1557 id = .minus_minus;
1558 self.index += 1;
1559 break;
1560 },
1561 else => {
1562 id = .minus;
1563 break;
1564 },
1565 },
1566 .ampersand => switch (c) {
1567 '&' => {
1568 id = .ampersand_ampersand;
1569 self.index += 1;
1570 break;
1571 },
1572 '=' => {
1573 id = .ampersand_equal;
1574 self.index += 1;
1575 break;
1576 },
1577 else => {
1578 id = .ampersand;
1579 break;
1580 },
1581 },
1582 .hash => switch (c) {
1583 '#' => {
1584 id = .hash_hash;
1585 self.index += 1;
1586 break;
1587 },
1588 else => {
1589 id = .hash;
1590 break;
1591 },
1592 },
1593 .hash_digraph => switch (c) {
1594 '%' => state = .hash_hash_digraph_partial,
1595 else => {
1596 id = .hash;
1597 break;
1598 },
1599 },
1600 .hash_hash_digraph_partial => switch (c) {
1601 ':' => {
1602 id = .hash_hash;
1603 self.index += 1;
1604 break;
1605 },
1606 else => {
1607 id = .hash;
1608 self.index -= 1; // re-tokenize the percent
1609 break;
1610 },
1611 },
1612 .slash => switch (c) {
1613 '/' => state = .line_comment,
1614 '*' => state = .multi_line_comment,
1615 '=' => {
1616 id = .slash_equal;
1617 self.index += 1;
1618 break;
1619 },
1620 else => {
1621 id = .slash;
1622 break;
1623 },
1624 },
1625 .line_comment => switch (c) {
1626 '\n' => {
1627 if (self.langopts.preserve_comments) {
1628 id = .comment;
1629 break;
1630 }
1631 self.index -= 1;
1632 state = .start;
1633 },
1634 else => {},
1635 },
1636 .multi_line_comment => switch (c) {
1637 '*' => state = .multi_line_comment_asterisk,
1638 '\n' => self.line += 1,
1639 else => {},
1640 },
1641 .multi_line_comment_asterisk => switch (c) {
1642 '/' => {
1643 if (self.langopts.preserve_comments) {
1644 self.index += 1;
1645 id = .comment;
1646 break;
1647 }
1648 state = .multi_line_comment_done;
1649 },
1650 '\n' => {
1651 self.line += 1;
1652 state = .multi_line_comment;
1653 },
1654 '*' => {},
1655 else => state = .multi_line_comment,
1656 },
1657 .multi_line_comment_done => switch (c) {
1658 '\n' => {
1659 start = self.index;
1660 id = .nl;
1661 self.index += 1;
1662 self.line += 1;
1663 break;
1664 },
1665 '\r' => unreachable,
1666 '\t', '\x0B', '\x0C', ' ' => {
1667 start = self.index;
1668 state = .whitespace;
1669 },
1670 else => {
1671 id = .whitespace;
1672 break;
1673 },
1674 },
1675 .pp_num => switch (c) {
1676 'a'...'d',
1677 'A'...'D',
1678 'f'...'o',
1679 'F'...'O',
1680 'q'...'z',
1681 'Q'...'Z',
1682 '0'...'9',
1683 '_',
1684 '.',
1685 => {},
1686 'e', 'E', 'p', 'P' => state = .pp_num_exponent,
1687 '\'' => if (self.langopts.standard.atLeast(.c23)) {
1688 state = .pp_num_digit_separator;
1689 } else {
1690 id = .pp_num;
1691 break;
1692 },
1693 else => {
1694 id = .pp_num;
1695 break;
1696 },
1697 },
1698 .pp_num_digit_separator => switch (c) {
1699 'a'...'d',
1700 'A'...'D',
1701 'f'...'o',
1702 'F'...'O',
1703 'q'...'z',
1704 'Q'...'Z',
1705 '0'...'9',
1706 '_',
1707 => state = .pp_num,
1708 else => {
1709 self.index -= 1;
1710 id = .pp_num;
1711 break;
1712 },
1713 },
1714 .pp_num_exponent => switch (c) {
1715 'a'...'o',
1716 'q'...'z',
1717 'A'...'O',
1718 'Q'...'Z',
1719 '0'...'9',
1720 '_',
1721 '.',
1722 '+',
1723 '-',
1724 => state = .pp_num,
1725 'p', 'P' => {},
1726 else => {
1727 id = .pp_num;
1728 break;
1729 },
1730 },
1731 }
1732 } else if (self.index == self.buf.len) {
1733 switch (state) {
1734 .start, .line_comment => {},
1735 .u, .u8, .U, .L, .identifier => id = Token.getTokenId(self.langopts, self.buf[start..self.index]),
1736 .extended_identifier => id = .extended_identifier,
1737
1738 .period2 => {
1739 self.index -= 1;
1740 id = .period;
1741 },
1742
1743 .multi_line_comment,
1744 .multi_line_comment_asterisk,
1745 => id = .unterminated_comment,
1746
1747 .char_escape_sequence, .char_literal, .char_literal_start => id = .unterminated_char_literal,
1748 .string_escape_sequence, .string_literal => id = .unterminated_string_literal,
1749
1750 .whitespace => id = .whitespace,
1751 .multi_line_comment_done => id = .whitespace,
1752
1753 .equal => id = .equal,
1754 .bang => id = .bang,
1755 .minus => id = .minus,
1756 .slash => id = .slash,
1757 .ampersand => id = .ampersand,
1758 .hash => id = .hash,
1759 .period => id = .period,
1760 .pipe => id = .pipe,
1761 .angle_bracket_angle_bracket_right => id = .angle_bracket_angle_bracket_right,
1762 .angle_bracket_right => id = .angle_bracket_right,
1763 .angle_bracket_angle_bracket_left => id = .angle_bracket_angle_bracket_left,
1764 .angle_bracket_left => id = .angle_bracket_left,
1765 .plus => id = .plus,
1766 .colon => id = .colon,
1767 .percent => id = .percent,
1768 .caret => id = .caret,
1769 .asterisk => id = .asterisk,
1770 .hash_digraph => id = .hash,
1771 .hash_hash_digraph_partial => {
1772 id = .hash;
1773 self.index -= 1; // re-tokenize the percent
1774 },
1775 .pp_num, .pp_num_exponent, .pp_num_digit_separator => id = .pp_num,
1776 }
1777 }
1778
1779 return .{
1780 .id = id,
1781 .start = start,
1782 .end = self.index,
1783 .line = self.line,
1784 .source = self.source,
1785 };
1786}
1787
1788pub fn nextNoWS(self: *Tokenizer) Token {
1789 var tok = self.next();
1790 while (tok.id == .whitespace or tok.id == .comment) tok = self.next();
1791 return tok;
1792}
1793
1794pub fn nextNoWSComments(self: *Tokenizer) Token {
1795 var tok = self.next();
1796 while (tok.id == .whitespace) tok = self.next();
1797 return tok;
1798}
1799
1800/// Try to tokenize a '::' even if not supported by the current language standard.
1801pub fn colonColon(self: *Tokenizer) Token {
1802 var tok = self.nextNoWS();
1803 if (tok.id == .colon and self.index < self.buf.len and self.buf[self.index] == ':') {
1804 self.index += 1;
1805 tok.id = .colon_colon;
1806 }
1807 return tok;
1808}
1809
1810test "operators" {
1811 try expectTokens(
1812 \\ ! != | || |= = ==
1813 \\ ( ) { } [ ] . .. ...
1814 \\ ^ ^= + ++ += - -- -=
1815 \\ * *= % %= -> : ; / /=
1816 \\ , & && &= ? < <= <<
1817 \\ <<= > >= >> >>= ~ # ##
1818 \\
1819 , &.{
1820 .bang,
1821 .bang_equal,
1822 .pipe,
1823 .pipe_pipe,
1824 .pipe_equal,
1825 .equal,
1826 .equal_equal,
1827 .nl,
1828 .l_paren,
1829 .r_paren,
1830 .l_brace,
1831 .r_brace,
1832 .l_bracket,
1833 .r_bracket,
1834 .period,
1835 .period,
1836 .period,
1837 .ellipsis,
1838 .nl,
1839 .caret,
1840 .caret_equal,
1841 .plus,
1842 .plus_plus,
1843 .plus_equal,
1844 .minus,
1845 .minus_minus,
1846 .minus_equal,
1847 .nl,
1848 .asterisk,
1849 .asterisk_equal,
1850 .percent,
1851 .percent_equal,
1852 .arrow,
1853 .colon,
1854 .semicolon,
1855 .slash,
1856 .slash_equal,
1857 .nl,
1858 .comma,
1859 .ampersand,
1860 .ampersand_ampersand,
1861 .ampersand_equal,
1862 .question_mark,
1863 .angle_bracket_left,
1864 .angle_bracket_left_equal,
1865 .angle_bracket_angle_bracket_left,
1866 .nl,
1867 .angle_bracket_angle_bracket_left_equal,
1868 .angle_bracket_right,
1869 .angle_bracket_right_equal,
1870 .angle_bracket_angle_bracket_right,
1871 .angle_bracket_angle_bracket_right_equal,
1872 .tilde,
1873 .hash,
1874 .hash_hash,
1875 .nl,
1876 });
1877}
1878
1879test "keywords" {
1880 try expectTokens(
1881 \\auto __auto_type break case char const continue default do
1882 \\double else enum extern float for goto if int
1883 \\long register return short signed sizeof static
1884 \\struct switch typedef union unsigned void volatile
1885 \\while _Bool _Complex _Imaginary inline restrict _Alignas
1886 \\_Alignof _Atomic _Generic _Noreturn _Static_assert _Thread_local
1887 \\__attribute __attribute__
1888 \\
1889 , &.{
1890 .keyword_auto,
1891 .keyword_auto_type,
1892 .keyword_break,
1893 .keyword_case,
1894 .keyword_char,
1895 .keyword_const,
1896 .keyword_continue,
1897 .keyword_default,
1898 .keyword_do,
1899 .nl,
1900 .keyword_double,
1901 .keyword_else,
1902 .keyword_enum,
1903 .keyword_extern,
1904 .keyword_float,
1905 .keyword_for,
1906 .keyword_goto,
1907 .keyword_if,
1908 .keyword_int,
1909 .nl,
1910 .keyword_long,
1911 .keyword_register,
1912 .keyword_return,
1913 .keyword_short,
1914 .keyword_signed,
1915 .keyword_sizeof,
1916 .keyword_static,
1917 .nl,
1918 .keyword_struct,
1919 .keyword_switch,
1920 .keyword_typedef,
1921 .keyword_union,
1922 .keyword_unsigned,
1923 .keyword_void,
1924 .keyword_volatile,
1925 .nl,
1926 .keyword_while,
1927 .keyword_bool,
1928 .keyword_complex,
1929 .keyword_imaginary,
1930 .keyword_inline,
1931 .keyword_restrict,
1932 .keyword_alignas,
1933 .nl,
1934 .keyword_alignof,
1935 .keyword_atomic,
1936 .keyword_generic,
1937 .keyword_noreturn,
1938 .keyword_static_assert,
1939 .keyword_thread_local,
1940 .nl,
1941 .keyword_attribute1,
1942 .keyword_attribute2,
1943 .nl,
1944 });
1945}
1946
1947test "preprocessor keywords" {
1948 try expectTokens(
1949 \\#include
1950 \\#include_next
1951 \\#embed
1952 \\#define
1953 \\#ifdef
1954 \\#ifndef
1955 \\#error
1956 \\#pragma
1957 \\
1958 , &.{
1959 .hash,
1960 .keyword_include,
1961 .nl,
1962 .hash,
1963 .keyword_include_next,
1964 .nl,
1965 .hash,
1966 .keyword_embed,
1967 .nl,
1968 .hash,
1969 .keyword_define,
1970 .nl,
1971 .hash,
1972 .keyword_ifdef,
1973 .nl,
1974 .hash,
1975 .keyword_ifndef,
1976 .nl,
1977 .hash,
1978 .keyword_error,
1979 .nl,
1980 .hash,
1981 .keyword_pragma,
1982 .nl,
1983 });
1984}
1985
1986test "line continuation" {
1987 try expectTokens(
1988 \\#define foo \
1989 \\ bar
1990 \\"foo\
1991 \\ bar"
1992 \\#define "foo"
1993 \\ "bar"
1994 \\#define "foo" \
1995 \\ "bar"
1996 , &.{
1997 .hash,
1998 .keyword_define,
1999 .identifier,
2000 .identifier,
2001 .nl,
2002 .string_literal,
2003 .nl,
2004 .hash,
2005 .keyword_define,
2006 .string_literal,
2007 .nl,
2008 .string_literal,
2009 .nl,
2010 .hash,
2011 .keyword_define,
2012 .string_literal,
2013 .string_literal,
2014 });
2015}
2016
2017test "string prefix" {
2018 try expectTokens(
2019 \\"foo"
2020 \\u"foo"
2021 \\u8"foo"
2022 \\U"foo"
2023 \\L"foo"
2024 \\'foo'
2025 \\u8'A'
2026 \\u'foo'
2027 \\U'foo'
2028 \\L'foo'
2029 \\
2030 , &.{
2031 .string_literal,
2032 .nl,
2033 .string_literal_utf_16,
2034 .nl,
2035 .string_literal_utf_8,
2036 .nl,
2037 .string_literal_utf_32,
2038 .nl,
2039 .string_literal_wide,
2040 .nl,
2041 .char_literal,
2042 .nl,
2043 .char_literal_utf_8,
2044 .nl,
2045 .char_literal_utf_16,
2046 .nl,
2047 .char_literal_utf_32,
2048 .nl,
2049 .char_literal_wide,
2050 .nl,
2051 });
2052}
2053
2054test "num suffixes" {
2055 try expectTokens(
2056 \\ 1.0f 1.0L 1.0 .0 1. 0x1p0f 0X1p0
2057 \\ 0l 0lu 0ll 0llu 0
2058 \\ 1u 1ul 1ull 1
2059 \\ 1.0i 1.0I
2060 \\ 1.0if 1.0If 1.0fi 1.0fI
2061 \\ 1.0il 1.0Il 1.0li 1.0lI
2062 \\
2063 , &.{
2064 .pp_num,
2065 .pp_num,
2066 .pp_num,
2067 .pp_num,
2068 .pp_num,
2069 .pp_num,
2070 .pp_num,
2071 .nl,
2072 .pp_num,
2073 .pp_num,
2074 .pp_num,
2075 .pp_num,
2076 .pp_num,
2077 .nl,
2078 .pp_num,
2079 .pp_num,
2080 .pp_num,
2081 .pp_num,
2082 .nl,
2083 .pp_num,
2084 .pp_num,
2085 .nl,
2086 .pp_num,
2087 .pp_num,
2088 .pp_num,
2089 .pp_num,
2090 .nl,
2091 .pp_num,
2092 .pp_num,
2093 .pp_num,
2094 .pp_num,
2095 .nl,
2096 });
2097}
2098
2099test "comments" {
2100 try expectTokens(
2101 \\//foo
2102 \\#foo
2103 , &.{
2104 .nl,
2105 .hash,
2106 .identifier,
2107 });
2108}
2109
2110test "extended identifiers" {
2111 try expectTokens("𝓪𝓻𝓸𝓬𝓬", &.{.extended_identifier});
2112 try expectTokens("u𝓪𝓻𝓸𝓬𝓬", &.{.extended_identifier});
2113 try expectTokens("u8𝓪𝓻𝓸𝓬𝓬", &.{.extended_identifier});
2114 try expectTokens("U𝓪𝓻𝓸𝓬𝓬", &.{.extended_identifier});
2115 try expectTokens("L𝓪𝓻𝓸𝓬𝓬", &.{.extended_identifier});
2116 try expectTokens("1™", &.{ .pp_num, .extended_identifier });
2117 try expectTokens("1.™", &.{ .pp_num, .extended_identifier });
2118 try expectTokens("..™", &.{ .period, .period, .extended_identifier });
2119 try expectTokens("0™", &.{ .pp_num, .extended_identifier });
2120 try expectTokens("0b\u{E0000}", &.{ .pp_num, .extended_identifier });
2121 try expectTokens("0b0\u{E0000}", &.{ .pp_num, .extended_identifier });
2122 try expectTokens("01\u{E0000}", &.{ .pp_num, .extended_identifier });
2123 try expectTokens("010\u{E0000}", &.{ .pp_num, .extended_identifier });
2124 try expectTokens("0x\u{E0000}", &.{ .pp_num, .extended_identifier });
2125 try expectTokens("0x0\u{E0000}", &.{ .pp_num, .extended_identifier });
2126 try expectTokens("\"\\0\u{E0000}\"", &.{.string_literal});
2127 try expectTokens("\"\\x\u{E0000}\"", &.{.string_literal});
2128 try expectTokens("\"\\u\u{E0000}\"", &.{.string_literal});
2129 try expectTokens("1e\u{E0000}", &.{ .pp_num, .extended_identifier });
2130 try expectTokens("1e1\u{E0000}", &.{ .pp_num, .extended_identifier });
2131}
2132
2133test "digraphs" {
2134 try expectTokens("%:<::><%%>%:%:", &.{ .hash, .l_bracket, .r_bracket, .l_brace, .r_brace, .hash_hash });
2135 try expectTokens("\"%:<::><%%>%:%:\"", &.{.string_literal});
2136 try expectTokens("%:%42 %:%", &.{ .hash, .percent, .pp_num, .hash, .percent });
2137}
2138
2139test "C23 keywords" {
2140 try expectTokensExtra("true false alignas alignof bool static_assert thread_local nullptr typeof_unqual", &.{
2141 .keyword_true,
2142 .keyword_false,
2143 .keyword_c23_alignas,
2144 .keyword_c23_alignof,
2145 .keyword_c23_bool,
2146 .keyword_c23_static_assert,
2147 .keyword_c23_thread_local,
2148 .keyword_nullptr,
2149 .keyword_typeof_unqual,
2150 }, .c23);
2151}
2152
2153test "Tokenizer fuzz test" {
2154 var comp = Compilation.init(std.testing.allocator, std.fs.cwd());
2155 defer comp.deinit();
2156
2157 const input_bytes = std.testing.fuzzInput(.{});
2158 if (input_bytes.len == 0) return;
2159
2160 const source = try comp.addSourceFromBuffer("fuzz.c", input_bytes);
2161
2162 var tokenizer: Tokenizer = .{
2163 .buf = source.buf,
2164 .source = source.id,
2165 .langopts = comp.langopts,
2166 };
2167 while (true) {
2168 const prev_index = tokenizer.index;
2169 const tok = tokenizer.next();
2170 if (tok.id == .eof) break;
2171 try std.testing.expect(prev_index < tokenizer.index); // ensure that the tokenizer always makes progress
2172 }
2173}
2174
2175fn expectTokensExtra(contents: []const u8, expected_tokens: []const Token.Id, standard: ?LangOpts.Standard) !void {
2176 var comp = Compilation.init(std.testing.allocator, std.fs.cwd());
2177 defer comp.deinit();
2178 if (standard) |provided| {
2179 comp.langopts.standard = provided;
2180 }
2181 const source = try comp.addSourceFromBuffer("path", contents);
2182 var tokenizer = Tokenizer{
2183 .buf = source.buf,
2184 .source = source.id,
2185 .langopts = comp.langopts,
2186 };
2187 var i: usize = 0;
2188 while (i < expected_tokens.len) {
2189 const token = tokenizer.next();
2190 if (token.id == .whitespace) continue;
2191 const expected_token_id = expected_tokens[i];
2192 i += 1;
2193 if (!std.meta.eql(token.id, expected_token_id)) {
2194 std.debug.print("expected {s}, found {s}\n", .{ @tagName(expected_token_id), @tagName(token.id) });
2195 return error.TokensDoNotEqual;
2196 }
2197 }
2198 const last_token = tokenizer.next();
2199 try std.testing.expect(last_token.id == .eof);
2200}
2201
2202fn expectTokens(contents: []const u8, expected_tokens: []const Token.Id) !void {
2203 return expectTokensExtra(contents, expected_tokens, null);
2204}
lib/compiler/aro/aro/Toolchain.zig deleted-508
...@@ -1,508 +0,0 @@
1const std = @import("std");
2const Driver = @import("Driver.zig");
3const Compilation = @import("Compilation.zig");
4const mem = std.mem;
5const system_defaults = @import("system_defaults");
6const target_util = @import("target.zig");
7const Linux = @import("toolchains/Linux.zig");
8const Multilib = @import("Driver/Multilib.zig");
9const Filesystem = @import("Driver/Filesystem.zig").Filesystem;
10
11pub const PathList = std.ArrayListUnmanaged([]const u8);
12
13pub const RuntimeLibKind = enum {
14 compiler_rt,
15 libgcc,
16};
17
18pub const FileKind = enum {
19 object,
20 static,
21 shared,
22};
23
24pub const LibGCCKind = enum {
25 unspecified,
26 static,
27 shared,
28};
29
30pub const UnwindLibKind = enum {
31 none,
32 compiler_rt,
33 libgcc,
34};
35
36const Inner = union(enum) {
37 uninitialized,
38 linux: Linux,
39 unknown: void,
40
41 fn deinit(self: *Inner, allocator: mem.Allocator) void {
42 switch (self.*) {
43 .linux => |*linux| linux.deinit(allocator),
44 .uninitialized, .unknown => {},
45 }
46 }
47};
48
49const Toolchain = @This();
50
51filesystem: Filesystem = .{ .real = {} },
52driver: *Driver,
53arena: mem.Allocator,
54
55/// The list of toolchain specific path prefixes to search for libraries.
56library_paths: PathList = .{},
57
58/// The list of toolchain specific path prefixes to search for files.
59file_paths: PathList = .{},
60
61/// The list of toolchain specific path prefixes to search for programs.
62program_paths: PathList = .{},
63
64selected_multilib: Multilib = .{},
65
66inner: Inner = .{ .uninitialized = {} },
67
68pub fn getTarget(tc: *const Toolchain) std.Target {
69 return tc.driver.comp.target;
70}
71
72fn getDefaultLinker(tc: *const Toolchain) []const u8 {
73 return switch (tc.inner) {
74 .uninitialized => unreachable,
75 .linux => |linux| linux.getDefaultLinker(tc.getTarget()),
76 .unknown => "ld",
77 };
78}
79
80/// Call this after driver has finished parsing command line arguments to find the toolchain
81pub fn discover(tc: *Toolchain) !void {
82 if (tc.inner != .uninitialized) return;
83
84 const target = tc.getTarget();
85 tc.inner = switch (target.os.tag) {
86 .elfiamcu,
87 .linux,
88 => if (target.cpu.arch == .hexagon)
89 .{ .unknown = {} } // TODO
90 else if (target.cpu.arch.isMIPS())
91 .{ .unknown = {} } // TODO
92 else if (target.cpu.arch.isPowerPC())
93 .{ .unknown = {} } // TODO
94 else if (target.cpu.arch == .ve)
95 .{ .unknown = {} } // TODO
96 else
97 .{ .linux = .{} },
98 else => .{ .unknown = {} }, // TODO
99 };
100 return switch (tc.inner) {
101 .uninitialized => unreachable,
102 .linux => |*linux| linux.discover(tc),
103 .unknown => {},
104 };
105}
106
107pub fn deinit(tc: *Toolchain) void {
108 const gpa = tc.driver.comp.gpa;
109 tc.inner.deinit(gpa);
110
111 tc.library_paths.deinit(gpa);
112 tc.file_paths.deinit(gpa);
113 tc.program_paths.deinit(gpa);
114}
115
116/// Write linker path to `buf` and return a slice of it
117pub fn getLinkerPath(tc: *const Toolchain, buf: []u8) ![]const u8 {
118 // --ld-path= takes precedence over -fuse-ld= and specifies the executable
119 // name. -B, COMPILER_PATH and PATH are consulted if the value does not
120 // contain a path component separator.
121 // -fuse-ld=lld can be used with --ld-path= to indicate that the binary
122 // that --ld-path= points to is lld.
123 const use_linker = tc.driver.use_linker orelse system_defaults.linker;
124
125 if (tc.driver.linker_path) |ld_path| {
126 var path = ld_path;
127 if (path.len > 0) {
128 if (std.fs.path.dirname(path) == null) {
129 path = tc.getProgramPath(path, buf);
130 }
131 if (tc.filesystem.canExecute(path)) {
132 return path;
133 }
134 }
135 return tc.driver.fatal(
136 "invalid linker name in argument '--ld-path={s}'",
137 .{path},
138 );
139 }
140
141 // If we're passed -fuse-ld= with no argument, or with the argument ld,
142 // then use whatever the default system linker is.
143 if (use_linker.len == 0 or mem.eql(u8, use_linker, "ld")) {
144 const default = tc.getDefaultLinker();
145 if (std.fs.path.isAbsolute(default)) return default;
146 return tc.getProgramPath(default, buf);
147 }
148
149 // Extending -fuse-ld= to an absolute or relative path is unexpected. Checking
150 // for the linker flavor is brittle. In addition, prepending "ld." or "ld64."
151 // to a relative path is surprising. This is more complex due to priorities
152 // among -B, COMPILER_PATH and PATH. --ld-path= should be used instead.
153 if (mem.indexOfScalar(u8, use_linker, '/') != null) {
154 try tc.driver.comp.addDiagnostic(.{ .tag = .fuse_ld_path }, &.{});
155 }
156
157 if (std.fs.path.isAbsolute(use_linker)) {
158 if (tc.filesystem.canExecute(use_linker)) {
159 return use_linker;
160 }
161 } else {
162 var linker_name = try std.ArrayList(u8).initCapacity(tc.driver.comp.gpa, 5 + use_linker.len); // "ld64." ++ use_linker
163 defer linker_name.deinit();
164 if (tc.getTarget().isDarwin()) {
165 linker_name.appendSliceAssumeCapacity("ld64.");
166 } else {
167 linker_name.appendSliceAssumeCapacity("ld.");
168 }
169 linker_name.appendSliceAssumeCapacity(use_linker);
170 const linker_path = tc.getProgramPath(linker_name.items, buf);
171 if (tc.filesystem.canExecute(linker_path)) {
172 return linker_path;
173 }
174 }
175
176 if (tc.driver.use_linker) |linker| {
177 return tc.driver.fatal(
178 "invalid linker name in argument '-fuse-ld={s}'",
179 .{linker},
180 );
181 }
182 const default_linker = tc.getDefaultLinker();
183 return tc.getProgramPath(default_linker, buf);
184}
185
186/// If an explicit target is provided, also check the prefixed tool-specific name
187/// TODO: this isn't exactly right since our target names don't necessarily match up
188/// with GCC's.
189/// For example the Zig target `arm-freestanding-eabi` would need the `arm-none-eabi` tools
190fn possibleProgramNames(raw_triple: ?[]const u8, name: []const u8, buf: *[64]u8) std.BoundedArray([]const u8, 2) {
191 var possible_names: std.BoundedArray([]const u8, 2) = .{};
192 if (raw_triple) |triple| {
193 if (std.fmt.bufPrint(buf, "{s}-{s}", .{ triple, name })) |res| {
194 possible_names.appendAssumeCapacity(res);
195 } else |_| {}
196 }
197 possible_names.appendAssumeCapacity(name);
198
199 return possible_names;
200}
201
202/// Add toolchain `file_paths` to argv as `-L` arguments
203pub fn addFilePathLibArgs(tc: *const Toolchain, argv: *std.ArrayList([]const u8)) !void {
204 try argv.ensureUnusedCapacity(tc.file_paths.items.len);
205
206 var bytes_needed: usize = 0;
207 for (tc.file_paths.items) |path| {
208 bytes_needed += path.len + 2; // +2 for `-L`
209 }
210 var bytes = try tc.arena.alloc(u8, bytes_needed);
211 var index: usize = 0;
212 for (tc.file_paths.items) |path| {
213 @memcpy(bytes[index..][0..2], "-L");
214 @memcpy(bytes[index + 2 ..][0..path.len], path);
215 argv.appendAssumeCapacity(bytes[index..][0 .. path.len + 2]);
216 index += path.len + 2;
217 }
218}
219
220/// Search for an executable called `name` or `{triple}-{name} in program_paths and the $PATH environment variable
221/// If not found there, just use `name`
222/// Writes the result to `buf` and returns a slice of it
223fn getProgramPath(tc: *const Toolchain, name: []const u8, buf: []u8) []const u8 {
224 var path_buf: [std.fs.max_path_bytes]u8 = undefined;
225 var fib = std.heap.FixedBufferAllocator.init(&path_buf);
226
227 var tool_specific_buf: [64]u8 = undefined;
228 const possible_names = possibleProgramNames(tc.driver.raw_target_triple, name, &tool_specific_buf);
229
230 for (possible_names.constSlice()) |tool_name| {
231 for (tc.program_paths.items) |program_path| {
232 defer fib.reset();
233
234 const candidate = std.fs.path.join(fib.allocator(), &.{ program_path, tool_name }) catch continue;
235
236 if (tc.filesystem.canExecute(candidate) and candidate.len <= buf.len) {
237 @memcpy(buf[0..candidate.len], candidate);
238 return buf[0..candidate.len];
239 }
240 }
241 return tc.filesystem.findProgramByName(tc.driver.comp.gpa, name, tc.driver.comp.environment.path, buf) orelse continue;
242 }
243 @memcpy(buf[0..name.len], name);
244 return buf[0..name.len];
245}
246
247pub fn getSysroot(tc: *const Toolchain) []const u8 {
248 return tc.driver.sysroot orelse system_defaults.sysroot;
249}
250
251/// Search for `name` in a variety of places
252/// TODO: cache results based on `name` so we're not repeatedly allocating the same strings?
253pub fn getFilePath(tc: *const Toolchain, name: []const u8) ![]const u8 {
254 var path_buf: [std.fs.max_path_bytes]u8 = undefined;
255 var fib = std.heap.FixedBufferAllocator.init(&path_buf);
256 const allocator = fib.allocator();
257
258 const sysroot = tc.getSysroot();
259
260 // todo check resource dir
261 // todo check compiler RT path
262 const aro_dir = std.fs.path.dirname(tc.driver.aro_name) orelse "";
263 const candidate = try std.fs.path.join(allocator, &.{ aro_dir, "..", name });
264 if (tc.filesystem.exists(candidate)) {
265 return tc.arena.dupe(u8, candidate);
266 }
267
268 if (tc.searchPaths(&fib, sysroot, tc.library_paths.items, name)) |path| {
269 return tc.arena.dupe(u8, path);
270 }
271
272 if (tc.searchPaths(&fib, sysroot, tc.file_paths.items, name)) |path| {
273 return try tc.arena.dupe(u8, path);
274 }
275
276 return name;
277}
278
279/// Search a list of `path_prefixes` for the existence `name`
280/// Assumes that `fba` is a fixed-buffer allocator, so does not free joined path candidates
281fn searchPaths(tc: *const Toolchain, fib: *std.heap.FixedBufferAllocator, sysroot: []const u8, path_prefixes: []const []const u8, name: []const u8) ?[]const u8 {
282 for (path_prefixes) |path| {
283 fib.reset();
284 if (path.len == 0) continue;
285
286 const candidate = if (path[0] == '=')
287 std.fs.path.join(fib.allocator(), &.{ sysroot, path[1..], name }) catch continue
288 else
289 std.fs.path.join(fib.allocator(), &.{ path, name }) catch continue;
290
291 if (tc.filesystem.exists(candidate)) {
292 return candidate;
293 }
294 }
295 return null;
296}
297
298const PathKind = enum {
299 library,
300 file,
301 program,
302};
303
304/// Join `components` into a path. If the path exists, dupe it into the toolchain arena and
305/// add it to the specified path list.
306pub fn addPathIfExists(tc: *Toolchain, components: []const []const u8, dest_kind: PathKind) !void {
307 var path_buf: [std.fs.max_path_bytes]u8 = undefined;
308 var fib = std.heap.FixedBufferAllocator.init(&path_buf);
309
310 const candidate = try std.fs.path.join(fib.allocator(), components);
311
312 if (tc.filesystem.exists(candidate)) {
313 const duped = try tc.arena.dupe(u8, candidate);
314 const dest = switch (dest_kind) {
315 .library => &tc.library_paths,
316 .file => &tc.file_paths,
317 .program => &tc.program_paths,
318 };
319 try dest.append(tc.driver.comp.gpa, duped);
320 }
321}
322
323/// Join `components` using the toolchain arena and add the resulting path to `dest_kind`. Does not check
324/// whether the path actually exists
325pub fn addPathFromComponents(tc: *Toolchain, components: []const []const u8, dest_kind: PathKind) !void {
326 const full_path = try std.fs.path.join(tc.arena, components);
327 const dest = switch (dest_kind) {
328 .library => &tc.library_paths,
329 .file => &tc.file_paths,
330 .program => &tc.program_paths,
331 };
332 try dest.append(tc.driver.comp.gpa, full_path);
333}
334
335/// Add linker args to `argv`. Does not add path to linker executable as first item; that must be handled separately
336/// Items added to `argv` will be string literals or owned by `tc.arena` so they must not be individually freed
337pub fn buildLinkerArgs(tc: *Toolchain, argv: *std.ArrayList([]const u8)) !void {
338 return switch (tc.inner) {
339 .uninitialized => unreachable,
340 .linux => |*linux| linux.buildLinkerArgs(tc, argv),
341 .unknown => @panic("This toolchain does not support linking yet"),
342 };
343}
344
345fn getDefaultRuntimeLibKind(tc: *const Toolchain) RuntimeLibKind {
346 if (tc.getTarget().isAndroid()) {
347 return .compiler_rt;
348 }
349 return .libgcc;
350}
351
352pub fn getRuntimeLibKind(tc: *const Toolchain) RuntimeLibKind {
353 const libname = tc.driver.rtlib orelse system_defaults.rtlib;
354 if (mem.eql(u8, libname, "compiler-rt"))
355 return .compiler_rt
356 else if (mem.eql(u8, libname, "libgcc"))
357 return .libgcc
358 else
359 return tc.getDefaultRuntimeLibKind();
360}
361
362/// TODO
363pub fn getCompilerRt(tc: *const Toolchain, component: []const u8, file_kind: FileKind) ![]const u8 {
364 _ = file_kind;
365 _ = component;
366 _ = tc;
367 return "";
368}
369
370fn getLibGCCKind(tc: *const Toolchain) LibGCCKind {
371 const target = tc.getTarget();
372 if (tc.driver.static_libgcc or tc.driver.static or tc.driver.static_pie or target.isAndroid()) {
373 return .static;
374 }
375 if (tc.driver.shared_libgcc) {
376 return .shared;
377 }
378 return .unspecified;
379}
380
381fn getUnwindLibKind(tc: *const Toolchain) !UnwindLibKind {
382 const libname = tc.driver.unwindlib orelse system_defaults.unwindlib;
383 if (libname.len == 0 or mem.eql(u8, libname, "platform")) {
384 switch (tc.getRuntimeLibKind()) {
385 .compiler_rt => {
386 const target = tc.getTarget();
387 if (target.isAndroid() or target.os.tag == .aix) {
388 return .compiler_rt;
389 } else {
390 return .none;
391 }
392 },
393 .libgcc => return .libgcc,
394 }
395 } else if (mem.eql(u8, libname, "none")) {
396 return .none;
397 } else if (mem.eql(u8, libname, "libgcc")) {
398 return .libgcc;
399 } else if (mem.eql(u8, libname, "libunwind")) {
400 if (tc.getRuntimeLibKind() == .libgcc) {
401 try tc.driver.comp.addDiagnostic(.{ .tag = .incompatible_unwindlib }, &.{});
402 }
403 return .compiler_rt;
404 } else {
405 unreachable;
406 }
407}
408
409fn getAsNeededOption(is_solaris: bool, needed: bool) []const u8 {
410 if (is_solaris) {
411 return if (needed) "-zignore" else "-zrecord";
412 } else {
413 return if (needed) "--as-needed" else "--no-as-needed";
414 }
415}
416
417fn addUnwindLibrary(tc: *const Toolchain, argv: *std.ArrayList([]const u8)) !void {
418 const unw = try tc.getUnwindLibKind();
419 const target = tc.getTarget();
420 if ((target.isAndroid() and unw == .libgcc) or
421 target.os.tag == .elfiamcu or
422 target.ofmt == .wasm or
423 target_util.isWindowsMSVCEnvironment(target) or
424 unw == .none) return;
425
426 const lgk = tc.getLibGCCKind();
427 const as_needed = lgk == .unspecified and !target.isAndroid() and !target_util.isCygwinMinGW(target) and target.os.tag != .aix;
428 if (as_needed) {
429 try argv.append(getAsNeededOption(target.os.tag == .solaris, true));
430 }
431 switch (unw) {
432 .none => return,
433 .libgcc => if (lgk == .static) try argv.append("-lgcc_eh") else try argv.append("-lgcc_s"),
434 .compiler_rt => if (target.os.tag == .aix) {
435 if (lgk != .static) {
436 try argv.append("-lunwind");
437 }
438 } else if (lgk == .static) {
439 try argv.append("-l:libunwind.a");
440 } else if (lgk == .shared) {
441 if (target_util.isCygwinMinGW(target)) {
442 try argv.append("-l:libunwind.dll.a");
443 } else {
444 try argv.append("-l:libunwind.so");
445 }
446 } else {
447 try argv.append("-lunwind");
448 },
449 }
450
451 if (as_needed) {
452 try argv.append(getAsNeededOption(target.os.tag == .solaris, false));
453 }
454}
455
456fn addLibGCC(tc: *const Toolchain, argv: *std.ArrayList([]const u8)) !void {
457 const libgcc_kind = tc.getLibGCCKind();
458 if (libgcc_kind == .static or libgcc_kind == .unspecified) {
459 try argv.append("-lgcc");
460 }
461 try tc.addUnwindLibrary(argv);
462 if (libgcc_kind == .shared) {
463 try argv.append("-lgcc");
464 }
465}
466
467pub fn addRuntimeLibs(tc: *const Toolchain, argv: *std.ArrayList([]const u8)) !void {
468 const target = tc.getTarget();
469 const rlt = tc.getRuntimeLibKind();
470 switch (rlt) {
471 .compiler_rt => {
472 // TODO
473 },
474 .libgcc => {
475 if (target_util.isKnownWindowsMSVCEnvironment(target)) {
476 const rtlib_str = tc.driver.rtlib orelse system_defaults.rtlib;
477 if (!mem.eql(u8, rtlib_str, "platform")) {
478 try tc.driver.comp.addDiagnostic(.{ .tag = .unsupported_rtlib_gcc, .extra = .{ .str = "MSVC" } }, &.{});
479 }
480 } else {
481 try tc.addLibGCC(argv);
482 }
483 },
484 }
485
486 if (target.isAndroid() and !tc.driver.static and !tc.driver.static_pie) {
487 try argv.append("-ldl");
488 }
489}
490
491pub fn defineSystemIncludes(tc: *Toolchain) !void {
492 return switch (tc.inner) {
493 .uninitialized => unreachable,
494 .linux => |*linux| linux.defineSystemIncludes(tc),
495 .unknown => {
496 if (tc.driver.nostdinc) return;
497
498 const comp = tc.driver.comp;
499 if (!tc.driver.nobuiltininc) {
500 try comp.addBuiltinIncludeDir(tc.driver.aro_name);
501 }
502
503 if (!tc.driver.nostdlibinc) {
504 try comp.addSystemIncludeDir("/usr/include");
505 }
506 },
507 };
508}
lib/compiler/aro/aro/Tree.zig deleted-1435
...@@ -1,1435 +0,0 @@
1const std = @import("std");
2const Interner = @import("../backend.zig").Interner;
3const Attribute = @import("Attribute.zig");
4const CodeGen = @import("CodeGen.zig");
5const Compilation = @import("Compilation.zig");
6const number_affixes = @import("Tree/number_affixes.zig");
7const Source = @import("Source.zig");
8const Tokenizer = @import("Tokenizer.zig");
9const Type = @import("Type.zig");
10const Value = @import("Value.zig");
11const StringInterner = @import("StringInterner.zig");
12
13pub const Token = struct {
14 id: Id,
15 loc: Source.Location,
16
17 pub const List = std.MultiArrayList(Token);
18 pub const Id = Tokenizer.Token.Id;
19 pub const NumberPrefix = number_affixes.Prefix;
20 pub const NumberSuffix = number_affixes.Suffix;
21};
22
23pub const TokenWithExpansionLocs = struct {
24 id: Token.Id,
25 flags: packed struct {
26 expansion_disabled: bool = false,
27 is_macro_arg: bool = false,
28 } = .{},
29 /// This location contains the actual token slice which might be generated.
30 /// If it is generated then there is guaranteed to be at least one
31 /// expansion location.
32 loc: Source.Location,
33 expansion_locs: ?[*]Source.Location = null,
34
35 pub fn expansionSlice(tok: TokenWithExpansionLocs) []const Source.Location {
36 const locs = tok.expansion_locs orelse return &[0]Source.Location{};
37 var i: usize = 0;
38 while (locs[i].id != .unused) : (i += 1) {}
39 return locs[0..i];
40 }
41
42 pub fn addExpansionLocation(tok: *TokenWithExpansionLocs, gpa: std.mem.Allocator, new: []const Source.Location) !void {
43 if (new.len == 0 or tok.id == .whitespace or tok.id == .macro_ws or tok.id == .placemarker) return;
44 var list = std.ArrayList(Source.Location).init(gpa);
45 defer {
46 @memset(list.items.ptr[list.items.len..list.capacity], .{});
47 // Add a sentinel to indicate the end of the list since
48 // the ArrayList's capacity isn't guaranteed to be exactly
49 // what we ask for.
50 if (list.capacity > 0) {
51 list.items.ptr[list.capacity - 1].byte_offset = 1;
52 }
53 tok.expansion_locs = list.items.ptr;
54 }
55
56 if (tok.expansion_locs) |locs| {
57 var i: usize = 0;
58 while (locs[i].id != .unused) : (i += 1) {}
59 list.items = locs[0..i];
60 while (locs[i].byte_offset != 1) : (i += 1) {}
61 list.capacity = i + 1;
62 }
63
64 const min_len = @max(list.items.len + new.len + 1, 4);
65 const wanted_len = std.math.ceilPowerOfTwo(usize, min_len) catch
66 return error.OutOfMemory;
67 try list.ensureTotalCapacity(wanted_len);
68
69 for (new) |new_loc| {
70 if (new_loc.id == .generated) continue;
71 list.appendAssumeCapacity(new_loc);
72 }
73 }
74
75 pub fn free(expansion_locs: ?[*]Source.Location, gpa: std.mem.Allocator) void {
76 const locs = expansion_locs orelse return;
77 var i: usize = 0;
78 while (locs[i].id != .unused) : (i += 1) {}
79 while (locs[i].byte_offset != 1) : (i += 1) {}
80 gpa.free(locs[0 .. i + 1]);
81 }
82
83 pub fn dupe(tok: TokenWithExpansionLocs, gpa: std.mem.Allocator) !TokenWithExpansionLocs {
84 var copy = tok;
85 copy.expansion_locs = null;
86 try copy.addExpansionLocation(gpa, tok.expansionSlice());
87 return copy;
88 }
89
90 pub fn checkMsEof(tok: TokenWithExpansionLocs, source: Source, comp: *Compilation) !void {
91 std.debug.assert(tok.id == .eof);
92 if (source.buf.len > tok.loc.byte_offset and source.buf[tok.loc.byte_offset] == 0x1A) {
93 try comp.addDiagnostic(.{
94 .tag = .ctrl_z_eof,
95 .loc = .{
96 .id = source.id,
97 .byte_offset = tok.loc.byte_offset,
98 .line = tok.loc.line,
99 },
100 }, &.{});
101 }
102 }
103};
104
105pub const TokenIndex = u32;
106pub const NodeIndex = enum(u32) { none, _ };
107pub const ValueMap = std.AutoHashMap(NodeIndex, Value);
108
109const Tree = @This();
110
111comp: *Compilation,
112arena: std.heap.ArenaAllocator,
113generated: []const u8,
114tokens: Token.List.Slice,
115nodes: Node.List.Slice,
116data: []const NodeIndex,
117root_decls: []const NodeIndex,
118value_map: ValueMap,
119
120pub const genIr = CodeGen.genIr;
121
122pub fn deinit(tree: *Tree) void {
123 tree.comp.gpa.free(tree.root_decls);
124 tree.comp.gpa.free(tree.data);
125 tree.nodes.deinit(tree.comp.gpa);
126 tree.arena.deinit();
127 tree.value_map.deinit();
128}
129
130pub const GNUAssemblyQualifiers = struct {
131 @"volatile": bool = false,
132 @"inline": bool = false,
133 goto: bool = false,
134};
135
136pub const Node = struct {
137 tag: Tag,
138 ty: Type = .{ .specifier = .void },
139 data: Data,
140 loc: Loc = .none,
141
142 pub const Range = struct { start: u32, end: u32 };
143
144 pub const Loc = enum(u32) {
145 none = std.math.maxInt(u32),
146 _,
147 };
148
149 pub const Data = union {
150 decl: struct {
151 name: TokenIndex,
152 node: NodeIndex = .none,
153 },
154 decl_ref: TokenIndex,
155 two: [2]NodeIndex,
156 range: Range,
157 if3: struct {
158 cond: NodeIndex,
159 body: u32,
160 },
161 un: NodeIndex,
162 bin: struct {
163 lhs: NodeIndex,
164 rhs: NodeIndex,
165 },
166 member: struct {
167 lhs: NodeIndex,
168 index: u32,
169 },
170 union_init: struct {
171 field_index: u32,
172 node: NodeIndex,
173 },
174 cast: struct {
175 operand: NodeIndex,
176 kind: CastKind,
177 },
178 int: u64,
179 return_zero: bool,
180
181 pub fn forDecl(data: Data, tree: *const Tree) struct {
182 decls: []const NodeIndex,
183 cond: NodeIndex,
184 incr: NodeIndex,
185 body: NodeIndex,
186 } {
187 const items = tree.data[data.range.start..data.range.end];
188 const decls = items[0 .. items.len - 3];
189
190 return .{
191 .decls = decls,
192 .cond = items[items.len - 3],
193 .incr = items[items.len - 2],
194 .body = items[items.len - 1],
195 };
196 }
197
198 pub fn forStmt(data: Data, tree: *const Tree) struct {
199 init: NodeIndex,
200 cond: NodeIndex,
201 incr: NodeIndex,
202 body: NodeIndex,
203 } {
204 const items = tree.data[data.if3.body..];
205
206 return .{
207 .init = items[0],
208 .cond = items[1],
209 .incr = items[2],
210 .body = data.if3.cond,
211 };
212 }
213 };
214
215 pub const List = std.MultiArrayList(Node);
216};
217
218pub const CastKind = enum(u8) {
219 /// Does nothing except possibly add qualifiers
220 no_op,
221 /// Interpret one bit pattern as another. Used for operands which have the same
222 /// size and unrelated types, e.g. casting one pointer type to another
223 bitcast,
224 /// Convert T[] to T *
225 array_to_pointer,
226 /// Converts an lvalue to an rvalue
227 lval_to_rval,
228 /// Convert a function type to a pointer to a function
229 function_to_pointer,
230 /// Convert a pointer type to a _Bool
231 pointer_to_bool,
232 /// Convert a pointer type to an integer type
233 pointer_to_int,
234 /// Convert _Bool to an integer type
235 bool_to_int,
236 /// Convert _Bool to a floating type
237 bool_to_float,
238 /// Convert a _Bool to a pointer; will cause a warning
239 bool_to_pointer,
240 /// Convert an integer type to _Bool
241 int_to_bool,
242 /// Convert an integer to a floating type
243 int_to_float,
244 /// Convert a complex integer to a complex floating type
245 complex_int_to_complex_float,
246 /// Convert an integer type to a pointer type
247 int_to_pointer,
248 /// Convert a floating type to a _Bool
249 float_to_bool,
250 /// Convert a floating type to an integer
251 float_to_int,
252 /// Convert a complex floating type to a complex integer
253 complex_float_to_complex_int,
254 /// Convert one integer type to another
255 int_cast,
256 /// Convert one complex integer type to another
257 complex_int_cast,
258 /// Convert real part of complex integer to a integer
259 complex_int_to_real,
260 /// Create a complex integer type using operand as the real part
261 real_to_complex_int,
262 /// Convert one floating type to another
263 float_cast,
264 /// Convert one complex floating type to another
265 complex_float_cast,
266 /// Convert real part of complex float to a float
267 complex_float_to_real,
268 /// Create a complex floating type using operand as the real part
269 real_to_complex_float,
270 /// Convert type to void
271 to_void,
272 /// Convert a literal 0 to a null pointer
273 null_to_pointer,
274 /// GNU cast-to-union extension
275 union_cast,
276 /// Create vector where each value is same as the input scalar.
277 vector_splat,
278};
279
280pub const Tag = enum(u8) {
281 /// Must appear at index 0. Also used as the tag for __builtin_types_compatible_p arguments, since the arguments are types
282 /// Reaching it is always the result of a bug.
283 invalid,
284
285 // ====== Decl ======
286
287 /// _Static_assert
288 /// loc is token index of _Static_assert
289 static_assert,
290
291 // function prototype
292 fn_proto,
293 static_fn_proto,
294 inline_fn_proto,
295 inline_static_fn_proto,
296
297 // function definition
298 fn_def,
299 static_fn_def,
300 inline_fn_def,
301 inline_static_fn_def,
302
303 // variable declaration
304 @"var",
305 extern_var,
306 static_var,
307 // same as static_var, used for __func__, __FUNCTION__ and __PRETTY_FUNCTION__
308 implicit_static_var,
309 threadlocal_var,
310 threadlocal_extern_var,
311 threadlocal_static_var,
312
313 /// __asm__("...") at file scope
314 /// loc is token index of __asm__ keyword
315 file_scope_asm,
316
317 // typedef declaration
318 typedef,
319
320 // container declarations
321 /// { two[0]; two[1]; }
322 struct_decl_two,
323 /// { two[0]; two[1]; }
324 union_decl_two,
325 /// { two[0], two[1], }
326 enum_decl_two,
327 /// { range }
328 struct_decl,
329 /// { range }
330 union_decl,
331 /// { range }
332 enum_decl,
333 /// struct decl_ref;
334 struct_forward_decl,
335 /// union decl_ref;
336 union_forward_decl,
337 /// enum decl_ref;
338 enum_forward_decl,
339
340 /// name = node
341 enum_field_decl,
342 /// ty name : node
343 /// name == 0 means unnamed
344 record_field_decl,
345 /// Used when a record has an unnamed record as a field
346 indirect_record_field_decl,
347
348 // ====== Stmt ======
349
350 labeled_stmt,
351 /// { two[0]; two[1]; } first and second may be null
352 compound_stmt_two,
353 /// { data }
354 compound_stmt,
355 /// if (first) data[second] else data[second+1];
356 if_then_else_stmt,
357 /// if (first) second; second may be null
358 if_then_stmt,
359 /// switch (first) second
360 switch_stmt,
361 /// case first: second
362 case_stmt,
363 /// case data[body]...data[body+1]: cond
364 case_range_stmt,
365 /// default: first
366 default_stmt,
367 /// while (first) second
368 while_stmt,
369 /// do second while(first);
370 do_while_stmt,
371 /// for (data[..]; data[len-3]; data[len-2]) data[len-1]
372 for_decl_stmt,
373 /// for (;;;) first
374 forever_stmt,
375 /// for (data[first]; data[first+1]; data[first+2]) second
376 for_stmt,
377 /// goto first;
378 goto_stmt,
379 /// goto *un;
380 computed_goto_stmt,
381 // continue; first and second unused
382 continue_stmt,
383 // break; first and second unused
384 break_stmt,
385 // null statement (just a semicolon); first and second unused
386 null_stmt,
387 /// return first; first may be null
388 return_stmt,
389 /// Assembly statement of the form __asm__("string literal")
390 gnu_asm_simple,
391
392 // ====== Expr ======
393
394 /// lhs , rhs
395 comma_expr,
396 /// lhs ? data[0] : data[1]
397 binary_cond_expr,
398 /// Used as the base for casts of the lhs in `binary_cond_expr`.
399 cond_dummy_expr,
400 /// lhs ? data[0] : data[1]
401 cond_expr,
402 /// lhs = rhs
403 assign_expr,
404 /// lhs *= rhs
405 mul_assign_expr,
406 /// lhs /= rhs
407 div_assign_expr,
408 /// lhs %= rhs
409 mod_assign_expr,
410 /// lhs += rhs
411 add_assign_expr,
412 /// lhs -= rhs
413 sub_assign_expr,
414 /// lhs <<= rhs
415 shl_assign_expr,
416 /// lhs >>= rhs
417 shr_assign_expr,
418 /// lhs &= rhs
419 bit_and_assign_expr,
420 /// lhs ^= rhs
421 bit_xor_assign_expr,
422 /// lhs |= rhs
423 bit_or_assign_expr,
424 /// lhs || rhs
425 bool_or_expr,
426 /// lhs && rhs
427 bool_and_expr,
428 /// lhs | rhs
429 bit_or_expr,
430 /// lhs ^ rhs
431 bit_xor_expr,
432 /// lhs & rhs
433 bit_and_expr,
434 /// lhs == rhs
435 equal_expr,
436 /// lhs != rhs
437 not_equal_expr,
438 /// lhs < rhs
439 less_than_expr,
440 /// lhs <= rhs
441 less_than_equal_expr,
442 /// lhs > rhs
443 greater_than_expr,
444 /// lhs >= rhs
445 greater_than_equal_expr,
446 /// lhs << rhs
447 shl_expr,
448 /// lhs >> rhs
449 shr_expr,
450 /// lhs + rhs
451 add_expr,
452 /// lhs - rhs
453 sub_expr,
454 /// lhs * rhs
455 mul_expr,
456 /// lhs / rhs
457 div_expr,
458 /// lhs % rhs
459 mod_expr,
460 /// Explicit: (type) cast
461 explicit_cast,
462 /// Implicit: cast
463 implicit_cast,
464 /// &un
465 addr_of_expr,
466 /// &&decl_ref
467 addr_of_label,
468 /// *un
469 deref_expr,
470 /// +un
471 plus_expr,
472 /// -un
473 negate_expr,
474 /// ~un
475 bit_not_expr,
476 /// !un
477 bool_not_expr,
478 /// ++un
479 pre_inc_expr,
480 /// --un
481 pre_dec_expr,
482 /// __imag un
483 imag_expr,
484 /// __real un
485 real_expr,
486 /// lhs[rhs] lhs is pointer/array type, rhs is integer type
487 array_access_expr,
488 /// two[0](two[1]) two[1] may be 0
489 call_expr_one,
490 /// data[0](data[1..])
491 call_expr,
492 /// decl
493 builtin_call_expr_one,
494 builtin_call_expr,
495 /// lhs.member
496 member_access_expr,
497 /// lhs->member
498 member_access_ptr_expr,
499 /// un++
500 post_inc_expr,
501 /// un--
502 post_dec_expr,
503 /// (un)
504 paren_expr,
505 /// decl_ref
506 decl_ref_expr,
507 /// decl_ref
508 enumeration_ref,
509 /// C23 bool literal `true` / `false`
510 bool_literal,
511 /// C23 nullptr literal
512 nullptr_literal,
513 /// integer literal, always unsigned
514 int_literal,
515 /// Same as int_literal, but originates from a char literal
516 char_literal,
517 /// a floating point literal
518 float_literal,
519 /// wraps a float or double literal: un
520 imaginary_literal,
521 /// tree.str[index..][0..len]
522 string_literal_expr,
523 /// sizeof(un?)
524 sizeof_expr,
525 /// _Alignof(un?)
526 alignof_expr,
527 /// _Generic(controlling two[0], chosen two[1])
528 generic_expr_one,
529 /// _Generic(controlling range[0], chosen range[1], rest range[2..])
530 generic_expr,
531 /// ty: un
532 generic_association_expr,
533 // default: un
534 generic_default_expr,
535 /// __builtin_choose_expr(lhs, data[0], data[1])
536 builtin_choose_expr,
537 /// __builtin_types_compatible_p(lhs, rhs)
538 builtin_types_compatible_p,
539 /// decl - special builtins require custom parsing
540 special_builtin_call_one,
541 /// ({ un })
542 stmt_expr,
543
544 // ====== Initializer expressions ======
545
546 /// { two[0], two[1] }
547 array_init_expr_two,
548 /// { range }
549 array_init_expr,
550 /// { two[0], two[1] }
551 struct_init_expr_two,
552 /// { range }
553 struct_init_expr,
554 /// { union_init }
555 union_init_expr,
556
557 /// (ty){ un }
558 /// loc is token index of l_paren
559 compound_literal_expr,
560 /// (static ty){ un }
561 /// loc is token index of l_paren
562 static_compound_literal_expr,
563 /// (thread_local ty){ un }
564 /// loc is token index of l_paren
565 thread_local_compound_literal_expr,
566 /// (static thread_local ty){ un }
567 /// loc is token index of l_paren
568 static_thread_local_compound_literal_expr,
569
570 /// Inserted at the end of a function body if no return stmt is found.
571 /// ty is the functions return type
572 /// data is return_zero which is true if the function is called "main" and ty is compatible with int
573 /// loc is token index of closing r_brace of function
574 implicit_return,
575
576 /// Inserted in array_init_expr to represent unspecified elements.
577 /// data.int contains the amount of elements.
578 array_filler_expr,
579 /// Inserted in record and scalar initializers for unspecified elements.
580 default_init_expr,
581
582 pub fn isImplicit(tag: Tag) bool {
583 return switch (tag) {
584 .implicit_cast,
585 .implicit_return,
586 .array_filler_expr,
587 .default_init_expr,
588 .implicit_static_var,
589 .cond_dummy_expr,
590 => true,
591 else => false,
592 };
593 }
594};
595
596pub fn isBitfield(tree: *const Tree, node: NodeIndex) bool {
597 return tree.bitfieldWidth(node, false) != null;
598}
599
600/// Returns null if node is not a bitfield. If inspect_lval is true, this function will
601/// recurse into implicit lval_to_rval casts (useful for arithmetic conversions)
602pub fn bitfieldWidth(tree: *const Tree, node: NodeIndex, inspect_lval: bool) ?u32 {
603 if (node == .none) return null;
604 switch (tree.nodes.items(.tag)[@intFromEnum(node)]) {
605 .member_access_expr, .member_access_ptr_expr => {
606 const member = tree.nodes.items(.data)[@intFromEnum(node)].member;
607 var ty = tree.nodes.items(.ty)[@intFromEnum(member.lhs)];
608 if (ty.isPtr()) ty = ty.elemType();
609 const record_ty = ty.get(.@"struct") orelse ty.get(.@"union") orelse return null;
610 const field = record_ty.data.record.fields[member.index];
611 return field.bit_width;
612 },
613 .implicit_cast => {
614 if (!inspect_lval) return null;
615
616 const data = tree.nodes.items(.data)[@intFromEnum(node)];
617 return switch (data.cast.kind) {
618 .lval_to_rval => tree.bitfieldWidth(data.cast.operand, false),
619 else => null,
620 };
621 },
622 else => return null,
623 }
624}
625
626const CallableResultUsage = struct {
627 /// name token of the thing being called, for diagnostics
628 tok: TokenIndex,
629 /// true if `nodiscard` attribute present
630 nodiscard: bool,
631 /// true if `warn_unused_result` attribute present
632 warn_unused_result: bool,
633};
634
635pub fn callableResultUsage(tree: *const Tree, node: NodeIndex) ?CallableResultUsage {
636 const data = tree.nodes.items(.data);
637
638 var cur_node = node;
639 while (true) switch (tree.nodes.items(.tag)[@intFromEnum(cur_node)]) {
640 .decl_ref_expr => {
641 const tok = data[@intFromEnum(cur_node)].decl_ref;
642 const fn_ty = tree.nodes.items(.ty)[@intFromEnum(node)].elemType();
643 return .{
644 .tok = tok,
645 .nodiscard = fn_ty.hasAttribute(.nodiscard),
646 .warn_unused_result = fn_ty.hasAttribute(.warn_unused_result),
647 };
648 },
649 .paren_expr => cur_node = data[@intFromEnum(cur_node)].un,
650 .comma_expr => cur_node = data[@intFromEnum(cur_node)].bin.rhs,
651
652 .explicit_cast, .implicit_cast => cur_node = data[@intFromEnum(cur_node)].cast.operand,
653 .addr_of_expr, .deref_expr => cur_node = data[@intFromEnum(cur_node)].un,
654 .call_expr_one => cur_node = data[@intFromEnum(cur_node)].two[0],
655 .call_expr => cur_node = tree.data[data[@intFromEnum(cur_node)].range.start],
656 .member_access_expr, .member_access_ptr_expr => {
657 const member = data[@intFromEnum(cur_node)].member;
658 var ty = tree.nodes.items(.ty)[@intFromEnum(member.lhs)];
659 if (ty.isPtr()) ty = ty.elemType();
660 const record = ty.getRecord().?;
661 const field = record.fields[member.index];
662 const attributes = if (record.field_attributes) |attrs| attrs[member.index] else &.{};
663 return .{
664 .tok = field.name_tok,
665 .nodiscard = for (attributes) |attr| {
666 if (attr.tag == .nodiscard) break true;
667 } else false,
668 .warn_unused_result = for (attributes) |attr| {
669 if (attr.tag == .warn_unused_result) break true;
670 } else false,
671 };
672 },
673 else => return null,
674 };
675}
676
677pub fn isLval(tree: *const Tree, node: NodeIndex) bool {
678 var is_const: bool = undefined;
679 return tree.isLvalExtra(node, &is_const);
680}
681
682pub fn isLvalExtra(tree: *const Tree, node: NodeIndex, is_const: *bool) bool {
683 is_const.* = false;
684 switch (tree.nodes.items(.tag)[@intFromEnum(node)]) {
685 .compound_literal_expr,
686 .static_compound_literal_expr,
687 .thread_local_compound_literal_expr,
688 .static_thread_local_compound_literal_expr,
689 => {
690 is_const.* = tree.nodes.items(.ty)[@intFromEnum(node)].isConst();
691 return true;
692 },
693 .string_literal_expr => return true,
694 .member_access_ptr_expr => {
695 const lhs_expr = tree.nodes.items(.data)[@intFromEnum(node)].member.lhs;
696 const ptr_ty = tree.nodes.items(.ty)[@intFromEnum(lhs_expr)];
697 if (ptr_ty.isPtr()) is_const.* = ptr_ty.elemType().isConst();
698 return true;
699 },
700 .array_access_expr => {
701 const lhs_expr = tree.nodes.items(.data)[@intFromEnum(node)].bin.lhs;
702 if (lhs_expr != .none) {
703 const array_ty = tree.nodes.items(.ty)[@intFromEnum(lhs_expr)];
704 if (array_ty.isPtr() or array_ty.isArray()) is_const.* = array_ty.elemType().isConst();
705 }
706 return true;
707 },
708 .decl_ref_expr => {
709 const decl_ty = tree.nodes.items(.ty)[@intFromEnum(node)];
710 is_const.* = decl_ty.isConst();
711 return true;
712 },
713 .deref_expr => {
714 const data = tree.nodes.items(.data)[@intFromEnum(node)];
715 const operand_ty = tree.nodes.items(.ty)[@intFromEnum(data.un)];
716 if (operand_ty.isFunc()) return false;
717 if (operand_ty.isPtr() or operand_ty.isArray()) is_const.* = operand_ty.elemType().isConst();
718 return true;
719 },
720 .member_access_expr => {
721 const data = tree.nodes.items(.data)[@intFromEnum(node)];
722 return tree.isLvalExtra(data.member.lhs, is_const);
723 },
724 .paren_expr => {
725 const data = tree.nodes.items(.data)[@intFromEnum(node)];
726 return tree.isLvalExtra(data.un, is_const);
727 },
728 .builtin_choose_expr => {
729 const data = tree.nodes.items(.data)[@intFromEnum(node)];
730
731 if (tree.value_map.get(data.if3.cond)) |val| {
732 const offset = @intFromBool(val.isZero(tree.comp));
733 return tree.isLvalExtra(tree.data[data.if3.body + offset], is_const);
734 }
735 return false;
736 },
737 else => return false,
738 }
739}
740
741/// This should only be used for node tags that represent AST nodes which have an arbitrary number of children
742/// It particular it should *not* be used for nodes with .un or .bin data types
743///
744/// For call expressions, child_nodes[0] is the function pointer being called and child_nodes[1..]
745/// are the arguments
746///
747/// For generic selection expressions, child_nodes[0] is the controlling expression,
748/// child_nodes[1] is the chosen expression (it is a syntax error for there to be no chosen expression),
749/// and child_nodes[2..] are the remaining expressions.
750pub fn childNodes(tree: *const Tree, node: NodeIndex) []const NodeIndex {
751 const tags = tree.nodes.items(.tag);
752 const data = tree.nodes.items(.data);
753 switch (tags[@intFromEnum(node)]) {
754 .compound_stmt_two,
755 .array_init_expr_two,
756 .struct_init_expr_two,
757 .enum_decl_two,
758 .struct_decl_two,
759 .union_decl_two,
760 .call_expr_one,
761 .generic_expr_one,
762 => {
763 const index: u32 = @intFromEnum(node);
764 const end = std.mem.indexOfScalar(NodeIndex, &data[index].two, .none) orelse 2;
765 return data[index].two[0..end];
766 },
767 .compound_stmt,
768 .array_init_expr,
769 .struct_init_expr,
770 .enum_decl,
771 .struct_decl,
772 .union_decl,
773 .call_expr,
774 .generic_expr,
775 => {
776 const range = data[@intFromEnum(node)].range;
777 return tree.data[range.start..range.end];
778 },
779 else => unreachable,
780 }
781}
782
783pub fn tokSlice(tree: *const Tree, tok_i: TokenIndex) []const u8 {
784 if (tree.tokens.items(.id)[tok_i].lexeme()) |some| return some;
785 const loc = tree.tokens.items(.loc)[tok_i];
786 return tree.comp.locSlice(loc);
787}
788
789pub fn nodeTok(tree: *const Tree, node: NodeIndex) ?TokenIndex {
790 std.debug.assert(node != .none);
791 const loc = tree.nodes.items(.loc)[@intFromEnum(node)];
792 return switch (loc) {
793 .none => null,
794 else => |tok_i| @intFromEnum(tok_i),
795 };
796}
797
798pub fn nodeLoc(tree: *const Tree, node: NodeIndex) ?Source.Location {
799 const tok_i = tree.nodeTok(node) orelse return null;
800 return tree.tokens.items(.loc)[@intFromEnum(tok_i)];
801}
802
803pub fn dump(tree: *const Tree, config: std.io.tty.Config, writer: anytype) !void {
804 const mapper = tree.comp.string_interner.getFastTypeMapper(tree.comp.gpa) catch tree.comp.string_interner.getSlowTypeMapper();
805 defer mapper.deinit(tree.comp.gpa);
806
807 for (tree.root_decls) |i| {
808 try tree.dumpNode(i, 0, mapper, config, writer);
809 try writer.writeByte('\n');
810 }
811}
812
813fn dumpFieldAttributes(tree: *const Tree, attributes: []const Attribute, level: u32, writer: anytype) !void {
814 for (attributes) |attr| {
815 try writer.writeByteNTimes(' ', level);
816 try writer.print("field attr: {s}", .{@tagName(attr.tag)});
817 try tree.dumpAttribute(attr, writer);
818 }
819}
820
821fn dumpAttribute(tree: *const Tree, attr: Attribute, writer: anytype) !void {
822 switch (attr.tag) {
823 inline else => |tag| {
824 const args = @field(attr.args, @tagName(tag));
825 const fields = @typeInfo(@TypeOf(args)).@"struct".fields;
826 if (fields.len == 0) {
827 try writer.writeByte('\n');
828 return;
829 }
830 try writer.writeByte(' ');
831 inline for (fields, 0..) |f, i| {
832 if (comptime std.mem.eql(u8, f.name, "__name_tok")) continue;
833 if (i != 0) {
834 try writer.writeAll(", ");
835 }
836 try writer.writeAll(f.name);
837 try writer.writeAll(": ");
838 switch (f.type) {
839 Interner.Ref => try writer.print("\"{s}\"", .{tree.interner.get(@field(args, f.name)).bytes}),
840 ?Interner.Ref => try writer.print("\"{?s}\"", .{if (@field(args, f.name)) |str| tree.interner.get(str).bytes else null}),
841 else => switch (@typeInfo(f.type)) {
842 .@"enum" => try writer.writeAll(@tagName(@field(args, f.name))),
843 else => try writer.print("{any}", .{@field(args, f.name)}),
844 },
845 }
846 }
847 try writer.writeByte('\n');
848 return;
849 },
850 }
851}
852
853fn dumpNode(
854 tree: *const Tree,
855 node: NodeIndex,
856 level: u32,
857 mapper: StringInterner.TypeMapper,
858 config: std.io.tty.Config,
859 w: anytype,
860) !void {
861 const delta = 2;
862 const half = delta / 2;
863 const TYPE = std.io.tty.Color.bright_magenta;
864 const TAG = std.io.tty.Color.bright_cyan;
865 const IMPLICIT = std.io.tty.Color.bright_blue;
866 const NAME = std.io.tty.Color.bright_red;
867 const LITERAL = std.io.tty.Color.bright_green;
868 const ATTRIBUTE = std.io.tty.Color.bright_yellow;
869 std.debug.assert(node != .none);
870
871 const tag = tree.nodes.items(.tag)[@intFromEnum(node)];
872 const data = tree.nodes.items(.data)[@intFromEnum(node)];
873 const ty = tree.nodes.items(.ty)[@intFromEnum(node)];
874 try w.writeByteNTimes(' ', level);
875
876 try config.setColor(w, if (tag.isImplicit()) IMPLICIT else TAG);
877 try w.print("{s}: ", .{@tagName(tag)});
878 if (tag == .implicit_cast or tag == .explicit_cast) {
879 try config.setColor(w, .white);
880 try w.print("({s}) ", .{@tagName(data.cast.kind)});
881 }
882 try config.setColor(w, TYPE);
883 try w.writeByte('\'');
884 const name = ty.getName();
885 if (name != .empty) {
886 try w.print("{s}': '", .{mapper.lookup(name)});
887 }
888 try ty.dump(mapper, tree.comp.langopts, w);
889 try w.writeByte('\'');
890
891 if (tree.isLval(node)) {
892 try config.setColor(w, ATTRIBUTE);
893 try w.writeAll(" lvalue");
894 }
895 if (tree.isBitfield(node)) {
896 try config.setColor(w, ATTRIBUTE);
897 try w.writeAll(" bitfield");
898 }
899 if (tree.value_map.get(node)) |val| {
900 try config.setColor(w, LITERAL);
901 try w.writeAll(" (value: ");
902 try val.print(ty, tree.comp, w);
903 try w.writeByte(')');
904 }
905 if (tag == .implicit_return and data.return_zero) {
906 try config.setColor(w, IMPLICIT);
907 try w.writeAll(" (value: 0)");
908 try config.setColor(w, .reset);
909 }
910
911 try w.writeAll("\n");
912 try config.setColor(w, .reset);
913
914 if (ty.specifier == .attributed) {
915 try config.setColor(w, ATTRIBUTE);
916 var it = Attribute.Iterator.initType(ty);
917 while (it.next()) |item| {
918 const attr, _ = item;
919 try w.writeByteNTimes(' ', level + half);
920 try w.print("attr: {s}", .{@tagName(attr.tag)});
921 try tree.dumpAttribute(attr, w);
922 }
923 try config.setColor(w, .reset);
924 }
925
926 switch (tag) {
927 .invalid => unreachable,
928 .file_scope_asm => {
929 try w.writeByteNTimes(' ', level + 1);
930 try tree.dumpNode(data.decl.node, level + delta, mapper, config, w);
931 },
932 .gnu_asm_simple => {
933 try w.writeByteNTimes(' ', level);
934 try tree.dumpNode(data.un, level, mapper, config, w);
935 },
936 .static_assert => {
937 try w.writeByteNTimes(' ', level + 1);
938 try w.writeAll("condition:\n");
939 try tree.dumpNode(data.bin.lhs, level + delta, mapper, config, w);
940 if (data.bin.rhs != .none) {
941 try w.writeByteNTimes(' ', level + 1);
942 try w.writeAll("diagnostic:\n");
943 try tree.dumpNode(data.bin.rhs, level + delta, mapper, config, w);
944 }
945 },
946 .fn_proto,
947 .static_fn_proto,
948 .inline_fn_proto,
949 .inline_static_fn_proto,
950 => {
951 try w.writeByteNTimes(' ', level + half);
952 try w.writeAll("name: ");
953 try config.setColor(w, NAME);
954 try w.print("{s}\n", .{tree.tokSlice(data.decl.name)});
955 try config.setColor(w, .reset);
956 },
957 .fn_def,
958 .static_fn_def,
959 .inline_fn_def,
960 .inline_static_fn_def,
961 => {
962 try w.writeByteNTimes(' ', level + half);
963 try w.writeAll("name: ");
964 try config.setColor(w, NAME);
965 try w.print("{s}\n", .{tree.tokSlice(data.decl.name)});
966 try config.setColor(w, .reset);
967 try w.writeByteNTimes(' ', level + half);
968 try w.writeAll("body:\n");
969 try tree.dumpNode(data.decl.node, level + delta, mapper, config, w);
970 },
971 .typedef,
972 .@"var",
973 .extern_var,
974 .static_var,
975 .implicit_static_var,
976 .threadlocal_var,
977 .threadlocal_extern_var,
978 .threadlocal_static_var,
979 => {
980 try w.writeByteNTimes(' ', level + half);
981 try w.writeAll("name: ");
982 try config.setColor(w, NAME);
983 try w.print("{s}\n", .{tree.tokSlice(data.decl.name)});
984 try config.setColor(w, .reset);
985 if (data.decl.node != .none) {
986 try w.writeByteNTimes(' ', level + half);
987 try w.writeAll("init:\n");
988 try tree.dumpNode(data.decl.node, level + delta, mapper, config, w);
989 }
990 },
991 .enum_field_decl => {
992 try w.writeByteNTimes(' ', level + half);
993 try w.writeAll("name: ");
994 try config.setColor(w, NAME);
995 try w.print("{s}\n", .{tree.tokSlice(data.decl.name)});
996 try config.setColor(w, .reset);
997 if (data.decl.node != .none) {
998 try w.writeByteNTimes(' ', level + half);
999 try w.writeAll("value:\n");
1000 try tree.dumpNode(data.decl.node, level + delta, mapper, config, w);
1001 }
1002 },
1003 .record_field_decl => {
1004 if (data.decl.name != 0) {
1005 try w.writeByteNTimes(' ', level + half);
1006 try w.writeAll("name: ");
1007 try config.setColor(w, NAME);
1008 try w.print("{s}\n", .{tree.tokSlice(data.decl.name)});
1009 try config.setColor(w, .reset);
1010 }
1011 if (data.decl.node != .none) {
1012 try w.writeByteNTimes(' ', level + half);
1013 try w.writeAll("bits:\n");
1014 try tree.dumpNode(data.decl.node, level + delta, mapper, config, w);
1015 }
1016 },
1017 .indirect_record_field_decl => {},
1018 .compound_stmt,
1019 .array_init_expr,
1020 .struct_init_expr,
1021 .enum_decl,
1022 .struct_decl,
1023 .union_decl,
1024 .compound_stmt_two,
1025 .array_init_expr_two,
1026 .struct_init_expr_two,
1027 .enum_decl_two,
1028 .struct_decl_two,
1029 .union_decl_two,
1030 => {
1031 const child_nodes = tree.childNodes(node);
1032 const maybe_field_attributes = if (ty.getRecord()) |record| record.field_attributes else null;
1033 for (child_nodes, 0..) |stmt, i| {
1034 if (i != 0) try w.writeByte('\n');
1035 try tree.dumpNode(stmt, level + delta, mapper, config, w);
1036 if (maybe_field_attributes) |field_attributes| {
1037 if (field_attributes[i].len == 0) continue;
1038
1039 try config.setColor(w, ATTRIBUTE);
1040 try tree.dumpFieldAttributes(field_attributes[i], level + delta + half, w);
1041 try config.setColor(w, .reset);
1042 }
1043 }
1044 },
1045 .union_init_expr => {
1046 try w.writeByteNTimes(' ', level + half);
1047 try w.writeAll("field index: ");
1048 try config.setColor(w, LITERAL);
1049 try w.print("{d}\n", .{data.union_init.field_index});
1050 try config.setColor(w, .reset);
1051 if (data.union_init.node != .none) {
1052 try tree.dumpNode(data.union_init.node, level + delta, mapper, config, w);
1053 }
1054 },
1055 .compound_literal_expr,
1056 .static_compound_literal_expr,
1057 .thread_local_compound_literal_expr,
1058 .static_thread_local_compound_literal_expr,
1059 => {
1060 try tree.dumpNode(data.un, level + half, mapper, config, w);
1061 },
1062 .labeled_stmt => {
1063 try w.writeByteNTimes(' ', level + half);
1064 try w.writeAll("label: ");
1065 try config.setColor(w, LITERAL);
1066 try w.print("{s}\n", .{tree.tokSlice(data.decl.name)});
1067 try config.setColor(w, .reset);
1068 if (data.decl.node != .none) {
1069 try w.writeByteNTimes(' ', level + half);
1070 try w.writeAll("stmt:\n");
1071 try tree.dumpNode(data.decl.node, level + delta, mapper, config, w);
1072 }
1073 },
1074 .case_stmt => {
1075 try w.writeByteNTimes(' ', level + half);
1076 try w.writeAll("value:\n");
1077 try tree.dumpNode(data.bin.lhs, level + delta, mapper, config, w);
1078 if (data.bin.rhs != .none) {
1079 try w.writeByteNTimes(' ', level + half);
1080 try w.writeAll("stmt:\n");
1081 try tree.dumpNode(data.bin.rhs, level + delta, mapper, config, w);
1082 }
1083 },
1084 .case_range_stmt => {
1085 try w.writeByteNTimes(' ', level + half);
1086 try w.writeAll("range start:\n");
1087 try tree.dumpNode(tree.data[data.if3.body], level + delta, mapper, config, w);
1088
1089 try w.writeByteNTimes(' ', level + half);
1090 try w.writeAll("range end:\n");
1091 try tree.dumpNode(tree.data[data.if3.body + 1], level + delta, mapper, config, w);
1092
1093 if (data.if3.cond != .none) {
1094 try w.writeByteNTimes(' ', level + half);
1095 try w.writeAll("stmt:\n");
1096 try tree.dumpNode(data.if3.cond, level + delta, mapper, config, w);
1097 }
1098 },
1099 .default_stmt => {
1100 if (data.un != .none) {
1101 try w.writeByteNTimes(' ', level + half);
1102 try w.writeAll("stmt:\n");
1103 try tree.dumpNode(data.un, level + delta, mapper, config, w);
1104 }
1105 },
1106 .binary_cond_expr, .cond_expr, .if_then_else_stmt, .builtin_choose_expr => {
1107 try w.writeByteNTimes(' ', level + half);
1108 try w.writeAll("cond:\n");
1109 try tree.dumpNode(data.if3.cond, level + delta, mapper, config, w);
1110
1111 try w.writeByteNTimes(' ', level + half);
1112 try w.writeAll("then:\n");
1113 try tree.dumpNode(tree.data[data.if3.body], level + delta, mapper, config, w);
1114
1115 try w.writeByteNTimes(' ', level + half);
1116 try w.writeAll("else:\n");
1117 try tree.dumpNode(tree.data[data.if3.body + 1], level + delta, mapper, config, w);
1118 },
1119 .builtin_types_compatible_p => {
1120 std.debug.assert(tree.nodes.items(.tag)[@intFromEnum(data.bin.lhs)] == .invalid);
1121 std.debug.assert(tree.nodes.items(.tag)[@intFromEnum(data.bin.rhs)] == .invalid);
1122
1123 try w.writeByteNTimes(' ', level + half);
1124 try w.writeAll("lhs: ");
1125
1126 const lhs_ty = tree.nodes.items(.ty)[@intFromEnum(data.bin.lhs)];
1127 try config.setColor(w, TYPE);
1128 try lhs_ty.dump(mapper, tree.comp.langopts, w);
1129 try config.setColor(w, .reset);
1130 try w.writeByte('\n');
1131
1132 try w.writeByteNTimes(' ', level + half);
1133 try w.writeAll("rhs: ");
1134
1135 const rhs_ty = tree.nodes.items(.ty)[@intFromEnum(data.bin.rhs)];
1136 try config.setColor(w, TYPE);
1137 try rhs_ty.dump(mapper, tree.comp.langopts, w);
1138 try config.setColor(w, .reset);
1139 try w.writeByte('\n');
1140 },
1141 .if_then_stmt => {
1142 try w.writeByteNTimes(' ', level + half);
1143 try w.writeAll("cond:\n");
1144 try tree.dumpNode(data.bin.lhs, level + delta, mapper, config, w);
1145
1146 if (data.bin.rhs != .none) {
1147 try w.writeByteNTimes(' ', level + half);
1148 try w.writeAll("then:\n");
1149 try tree.dumpNode(data.bin.rhs, level + delta, mapper, config, w);
1150 }
1151 },
1152 .switch_stmt, .while_stmt, .do_while_stmt => {
1153 try w.writeByteNTimes(' ', level + half);
1154 try w.writeAll("cond:\n");
1155 try tree.dumpNode(data.bin.lhs, level + delta, mapper, config, w);
1156
1157 if (data.bin.rhs != .none) {
1158 try w.writeByteNTimes(' ', level + half);
1159 try w.writeAll("body:\n");
1160 try tree.dumpNode(data.bin.rhs, level + delta, mapper, config, w);
1161 }
1162 },
1163 .for_decl_stmt => {
1164 const for_decl = data.forDecl(tree);
1165
1166 try w.writeByteNTimes(' ', level + half);
1167 try w.writeAll("decl:\n");
1168 for (for_decl.decls) |decl| {
1169 try tree.dumpNode(decl, level + delta, mapper, config, w);
1170 try w.writeByte('\n');
1171 }
1172 if (for_decl.cond != .none) {
1173 try w.writeByteNTimes(' ', level + half);
1174 try w.writeAll("cond:\n");
1175 try tree.dumpNode(for_decl.cond, level + delta, mapper, config, w);
1176 }
1177 if (for_decl.incr != .none) {
1178 try w.writeByteNTimes(' ', level + half);
1179 try w.writeAll("incr:\n");
1180 try tree.dumpNode(for_decl.incr, level + delta, mapper, config, w);
1181 }
1182 if (for_decl.body != .none) {
1183 try w.writeByteNTimes(' ', level + half);
1184 try w.writeAll("body:\n");
1185 try tree.dumpNode(for_decl.body, level + delta, mapper, config, w);
1186 }
1187 },
1188 .forever_stmt => {
1189 if (data.un != .none) {
1190 try w.writeByteNTimes(' ', level + half);
1191 try w.writeAll("body:\n");
1192 try tree.dumpNode(data.un, level + delta, mapper, config, w);
1193 }
1194 },
1195 .for_stmt => {
1196 const for_stmt = data.forStmt(tree);
1197
1198 if (for_stmt.init != .none) {
1199 try w.writeByteNTimes(' ', level + half);
1200 try w.writeAll("init:\n");
1201 try tree.dumpNode(for_stmt.init, level + delta, mapper, config, w);
1202 }
1203 if (for_stmt.cond != .none) {
1204 try w.writeByteNTimes(' ', level + half);
1205 try w.writeAll("cond:\n");
1206 try tree.dumpNode(for_stmt.cond, level + delta, mapper, config, w);
1207 }
1208 if (for_stmt.incr != .none) {
1209 try w.writeByteNTimes(' ', level + half);
1210 try w.writeAll("incr:\n");
1211 try tree.dumpNode(for_stmt.incr, level + delta, mapper, config, w);
1212 }
1213 if (for_stmt.body != .none) {
1214 try w.writeByteNTimes(' ', level + half);
1215 try w.writeAll("body:\n");
1216 try tree.dumpNode(for_stmt.body, level + delta, mapper, config, w);
1217 }
1218 },
1219 .goto_stmt, .addr_of_label => {
1220 try w.writeByteNTimes(' ', level + half);
1221 try w.writeAll("label: ");
1222 try config.setColor(w, LITERAL);
1223 try w.print("{s}\n", .{tree.tokSlice(data.decl_ref)});
1224 try config.setColor(w, .reset);
1225 },
1226 .continue_stmt, .break_stmt, .implicit_return, .null_stmt => {},
1227 .return_stmt => {
1228 if (data.un != .none) {
1229 try w.writeByteNTimes(' ', level + half);
1230 try w.writeAll("expr:\n");
1231 try tree.dumpNode(data.un, level + delta, mapper, config, w);
1232 }
1233 },
1234 .call_expr, .call_expr_one => {
1235 const child_nodes = tree.childNodes(node);
1236 const fn_ptr = child_nodes[0];
1237 const args = child_nodes[1..];
1238
1239 try w.writeByteNTimes(' ', level + half);
1240 try w.writeAll("lhs:\n");
1241 try tree.dumpNode(fn_ptr, level + delta, mapper, config, w);
1242
1243 if (args.len > 0) {
1244 try w.writeByteNTimes(' ', level + half);
1245 try w.writeAll("args:\n");
1246 for (args) |arg| {
1247 try tree.dumpNode(arg, level + delta, mapper, config, w);
1248 }
1249 }
1250 },
1251 .builtin_call_expr => {
1252 try w.writeByteNTimes(' ', level + half);
1253 try w.writeAll("name: ");
1254 try config.setColor(w, NAME);
1255 try w.print("{s}\n", .{tree.tokSlice(@intFromEnum(tree.data[data.range.start]))});
1256 try config.setColor(w, .reset);
1257
1258 try w.writeByteNTimes(' ', level + half);
1259 try w.writeAll("args:\n");
1260 for (tree.data[data.range.start + 1 .. data.range.end]) |arg| try tree.dumpNode(arg, level + delta, mapper, config, w);
1261 },
1262 .builtin_call_expr_one => {
1263 try w.writeByteNTimes(' ', level + half);
1264 try w.writeAll("name: ");
1265 try config.setColor(w, NAME);
1266 try w.print("{s}\n", .{tree.tokSlice(data.decl.name)});
1267 try config.setColor(w, .reset);
1268 if (data.decl.node != .none) {
1269 try w.writeByteNTimes(' ', level + half);
1270 try w.writeAll("arg:\n");
1271 try tree.dumpNode(data.decl.node, level + delta, mapper, config, w);
1272 }
1273 },
1274 .special_builtin_call_one => {
1275 try w.writeByteNTimes(' ', level + half);
1276 try w.writeAll("name: ");
1277 try config.setColor(w, NAME);
1278 try w.print("{s}\n", .{tree.tokSlice(data.decl.name)});
1279 try config.setColor(w, .reset);
1280 if (data.decl.node != .none) {
1281 try w.writeByteNTimes(' ', level + half);
1282 try w.writeAll("arg:\n");
1283 try tree.dumpNode(data.decl.node, level + delta, mapper, config, w);
1284 }
1285 },
1286 .comma_expr,
1287 .assign_expr,
1288 .mul_assign_expr,
1289 .div_assign_expr,
1290 .mod_assign_expr,
1291 .add_assign_expr,
1292 .sub_assign_expr,
1293 .shl_assign_expr,
1294 .shr_assign_expr,
1295 .bit_and_assign_expr,
1296 .bit_xor_assign_expr,
1297 .bit_or_assign_expr,
1298 .bool_or_expr,
1299 .bool_and_expr,
1300 .bit_or_expr,
1301 .bit_xor_expr,
1302 .bit_and_expr,
1303 .equal_expr,
1304 .not_equal_expr,
1305 .less_than_expr,
1306 .less_than_equal_expr,
1307 .greater_than_expr,
1308 .greater_than_equal_expr,
1309 .shl_expr,
1310 .shr_expr,
1311 .add_expr,
1312 .sub_expr,
1313 .mul_expr,
1314 .div_expr,
1315 .mod_expr,
1316 => {
1317 try w.writeByteNTimes(' ', level + 1);
1318 try w.writeAll("lhs:\n");
1319 try tree.dumpNode(data.bin.lhs, level + delta, mapper, config, w);
1320 try w.writeByteNTimes(' ', level + 1);
1321 try w.writeAll("rhs:\n");
1322 try tree.dumpNode(data.bin.rhs, level + delta, mapper, config, w);
1323 },
1324 .explicit_cast, .implicit_cast => try tree.dumpNode(data.cast.operand, level + delta, mapper, config, w),
1325 .addr_of_expr,
1326 .computed_goto_stmt,
1327 .deref_expr,
1328 .plus_expr,
1329 .negate_expr,
1330 .bit_not_expr,
1331 .bool_not_expr,
1332 .pre_inc_expr,
1333 .pre_dec_expr,
1334 .imag_expr,
1335 .real_expr,
1336 .post_inc_expr,
1337 .post_dec_expr,
1338 .paren_expr,
1339 => {
1340 try w.writeByteNTimes(' ', level + 1);
1341 try w.writeAll("operand:\n");
1342 try tree.dumpNode(data.un, level + delta, mapper, config, w);
1343 },
1344 .decl_ref_expr => {
1345 try w.writeByteNTimes(' ', level + 1);
1346 try w.writeAll("name: ");
1347 try config.setColor(w, NAME);
1348 try w.print("{s}\n", .{tree.tokSlice(data.decl_ref)});
1349 try config.setColor(w, .reset);
1350 },
1351 .enumeration_ref => {
1352 try w.writeByteNTimes(' ', level + 1);
1353 try w.writeAll("name: ");
1354 try config.setColor(w, NAME);
1355 try w.print("{s}\n", .{tree.tokSlice(data.decl_ref)});
1356 try config.setColor(w, .reset);
1357 },
1358 .bool_literal,
1359 .nullptr_literal,
1360 .int_literal,
1361 .char_literal,
1362 .float_literal,
1363 .string_literal_expr,
1364 => {},
1365 .member_access_expr, .member_access_ptr_expr => {
1366 try w.writeByteNTimes(' ', level + 1);
1367 try w.writeAll("lhs:\n");
1368 try tree.dumpNode(data.member.lhs, level + delta, mapper, config, w);
1369
1370 var lhs_ty = tree.nodes.items(.ty)[@intFromEnum(data.member.lhs)];
1371 if (lhs_ty.isPtr()) lhs_ty = lhs_ty.elemType();
1372 lhs_ty = lhs_ty.canonicalize(.standard);
1373
1374 try w.writeByteNTimes(' ', level + 1);
1375 try w.writeAll("name: ");
1376 try config.setColor(w, NAME);
1377 try w.print("{s}\n", .{mapper.lookup(lhs_ty.data.record.fields[data.member.index].name)});
1378 try config.setColor(w, .reset);
1379 },
1380 .array_access_expr => {
1381 if (data.bin.lhs != .none) {
1382 try w.writeByteNTimes(' ', level + 1);
1383 try w.writeAll("lhs:\n");
1384 try tree.dumpNode(data.bin.lhs, level + delta, mapper, config, w);
1385 }
1386 try w.writeByteNTimes(' ', level + 1);
1387 try w.writeAll("index:\n");
1388 try tree.dumpNode(data.bin.rhs, level + delta, mapper, config, w);
1389 },
1390 .sizeof_expr, .alignof_expr => {
1391 if (data.un != .none) {
1392 try w.writeByteNTimes(' ', level + 1);
1393 try w.writeAll("expr:\n");
1394 try tree.dumpNode(data.un, level + delta, mapper, config, w);
1395 }
1396 },
1397 .generic_expr, .generic_expr_one => {
1398 const child_nodes = tree.childNodes(node);
1399 const controlling = child_nodes[0];
1400 const chosen = child_nodes[1];
1401 const rest = child_nodes[2..];
1402
1403 try w.writeByteNTimes(' ', level + 1);
1404 try w.writeAll("controlling:\n");
1405 try tree.dumpNode(controlling, level + delta, mapper, config, w);
1406 try w.writeByteNTimes(' ', level + 1);
1407 try w.writeAll("chosen:\n");
1408 try tree.dumpNode(chosen, level + delta, mapper, config, w);
1409
1410 if (rest.len > 0) {
1411 try w.writeByteNTimes(' ', level + 1);
1412 try w.writeAll("rest:\n");
1413 for (rest) |expr| {
1414 try tree.dumpNode(expr, level + delta, mapper, config, w);
1415 }
1416 }
1417 },
1418 .generic_association_expr, .generic_default_expr, .stmt_expr, .imaginary_literal => {
1419 try tree.dumpNode(data.un, level + delta, mapper, config, w);
1420 },
1421 .array_filler_expr => {
1422 try w.writeByteNTimes(' ', level + 1);
1423 try w.writeAll("count: ");
1424 try config.setColor(w, LITERAL);
1425 try w.print("{d}\n", .{data.int});
1426 try config.setColor(w, .reset);
1427 },
1428 .struct_forward_decl,
1429 .union_forward_decl,
1430 .enum_forward_decl,
1431 .default_init_expr,
1432 .cond_dummy_expr,
1433 => {},
1434 }
1435}
lib/compiler/aro/aro/Tree/number_affixes.zig deleted-192
...@@ -1,192 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3
4pub const Prefix = enum(u8) {
5 binary = 2,
6 octal = 8,
7 decimal = 10,
8 hex = 16,
9
10 pub fn digitAllowed(prefix: Prefix, c: u8) bool {
11 return switch (c) {
12 '0', '1' => true,
13 '2'...'7' => prefix != .binary,
14 '8'...'9' => prefix == .decimal or prefix == .hex,
15 'a'...'f', 'A'...'F' => prefix == .hex,
16 else => false,
17 };
18 }
19
20 pub fn fromString(buf: []const u8) Prefix {
21 if (buf.len == 1) return .decimal;
22 // tokenizer enforces that first byte is a decimal digit or period
23 switch (buf[0]) {
24 '.', '1'...'9' => return .decimal,
25 '0' => {},
26 else => unreachable,
27 }
28 switch (buf[1]) {
29 'x', 'X' => return if (buf.len == 2) .decimal else .hex,
30 'b', 'B' => return if (buf.len == 2) .decimal else .binary,
31 else => {
32 if (mem.indexOfAny(u8, buf, "eE.")) |_| {
33 // This is a decimal floating point number that happens to start with zero
34 return .decimal;
35 } else if (Suffix.fromString(buf[1..], .int)) |_| {
36 // This is `0` with a valid suffix
37 return .decimal;
38 } else {
39 return .octal;
40 }
41 },
42 }
43 }
44
45 /// Length of this prefix as a string
46 pub fn stringLen(prefix: Prefix) usize {
47 return switch (prefix) {
48 .binary => 2,
49 .octal => 1,
50 .decimal => 0,
51 .hex => 2,
52 };
53 }
54};
55
56pub const Suffix = enum {
57 // zig fmt: off
58
59 // int and imaginary int
60 None, I,
61
62 // unsigned real integers
63 U, UL, ULL,
64
65 // unsigned imaginary integers
66 IU, IUL, IULL,
67
68 // long or long double, real and imaginary
69 L, IL,
70
71 // long long and imaginary long long
72 LL, ILL,
73
74 // float and imaginary float
75 F, IF,
76
77 // _Float16 and imaginary _Float16
78 F16, IF16,
79
80 // __float80
81 W,
82
83 // Imaginary __float80
84 IW,
85
86 // _Float128
87 Q, F128,
88
89 // Imaginary _Float128
90 IQ, IF128,
91
92 // Imaginary _Bitint
93 IWB, IUWB,
94
95 // _Bitint
96 WB, UWB,
97
98 // zig fmt: on
99
100 const Tuple = struct { Suffix, []const []const u8 };
101
102 const IntSuffixes = &[_]Tuple{
103 .{ .U, &.{"U"} },
104 .{ .L, &.{"L"} },
105 .{ .WB, &.{"WB"} },
106 .{ .UL, &.{ "U", "L" } },
107 .{ .UWB, &.{ "U", "WB" } },
108 .{ .LL, &.{"LL"} },
109 .{ .ULL, &.{ "U", "LL" } },
110
111 .{ .I, &.{"I"} },
112
113 .{ .IWB, &.{ "I", "WB" } },
114 .{ .IU, &.{ "I", "U" } },
115 .{ .IL, &.{ "I", "L" } },
116 .{ .IUL, &.{ "I", "U", "L" } },
117 .{ .IUWB, &.{ "I", "U", "WB" } },
118 .{ .ILL, &.{ "I", "LL" } },
119 .{ .IULL, &.{ "I", "U", "LL" } },
120 };
121
122 const FloatSuffixes = &[_]Tuple{
123 .{ .F16, &.{"F16"} },
124 .{ .F, &.{"F"} },
125 .{ .L, &.{"L"} },
126 .{ .W, &.{"W"} },
127 .{ .F128, &.{"F128"} },
128 .{ .Q, &.{"Q"} },
129
130 .{ .I, &.{"I"} },
131 .{ .IL, &.{ "I", "L" } },
132 .{ .IF16, &.{ "I", "F16" } },
133 .{ .IF, &.{ "I", "F" } },
134 .{ .IW, &.{ "I", "W" } },
135 .{ .IF128, &.{ "I", "F128" } },
136 .{ .IQ, &.{ "I", "Q" } },
137 };
138
139 pub fn fromString(buf: []const u8, suffix_kind: enum { int, float }) ?Suffix {
140 if (buf.len == 0) return .None;
141
142 const suffixes = switch (suffix_kind) {
143 .float => FloatSuffixes,
144 .int => IntSuffixes,
145 };
146 var scratch: [4]u8 = undefined;
147 top: for (suffixes) |candidate| {
148 const tag = candidate[0];
149 const parts = candidate[1];
150 var len: usize = 0;
151 for (parts) |part| len += part.len;
152 if (len != buf.len) continue;
153
154 for (parts) |part| {
155 const lower = std.ascii.lowerString(&scratch, part);
156 if (mem.indexOf(u8, buf, part) == null and mem.indexOf(u8, buf, lower) == null) continue :top;
157 }
158 return tag;
159 }
160 return null;
161 }
162
163 pub fn isImaginary(suffix: Suffix) bool {
164 return switch (suffix) {
165 .I, .IL, .IF, .IU, .IUL, .ILL, .IULL, .IWB, .IUWB, .IF128, .IQ, .IW, .IF16 => true,
166 .None, .L, .F16, .F, .U, .UL, .LL, .ULL, .WB, .UWB, .F128, .Q, .W => false,
167 };
168 }
169
170 pub fn isSignedInteger(suffix: Suffix) bool {
171 return switch (suffix) {
172 .None, .L, .LL, .I, .IL, .ILL, .WB, .IWB => true,
173 .U, .UL, .ULL, .IU, .IUL, .IULL, .UWB, .IUWB => false,
174 .F, .IF, .F16, .F128, .IF128, .Q, .IQ, .W, .IW, .IF16 => unreachable,
175 };
176 }
177
178 pub fn signedness(suffix: Suffix) std.builtin.Signedness {
179 return if (suffix.isSignedInteger()) .signed else .unsigned;
180 }
181
182 pub fn isBitInt(suffix: Suffix) bool {
183 return switch (suffix) {
184 .WB, .UWB, .IWB, .IUWB => true,
185 else => false,
186 };
187 }
188
189 pub fn isFloat80(suffix: Suffix) bool {
190 return suffix == .W or suffix == .IW;
191 }
192};
lib/compiler/aro/aro/Type.zig deleted-2675
...@@ -1,2675 +0,0 @@
1const std = @import("std");
2const Tree = @import("Tree.zig");
3const TokenIndex = Tree.TokenIndex;
4const NodeIndex = Tree.NodeIndex;
5const Parser = @import("Parser.zig");
6const Compilation = @import("Compilation.zig");
7const Attribute = @import("Attribute.zig");
8const StringInterner = @import("StringInterner.zig");
9const StringId = StringInterner.StringId;
10const target_util = @import("target.zig");
11const LangOpts = @import("LangOpts.zig");
12
13pub const Qualifiers = packed struct {
14 @"const": bool = false,
15 atomic: bool = false,
16 @"volatile": bool = false,
17 restrict: bool = false,
18
19 // for function parameters only, stored here since it fits in the padding
20 register: bool = false,
21
22 pub fn any(quals: Qualifiers) bool {
23 return quals.@"const" or quals.restrict or quals.@"volatile" or quals.atomic;
24 }
25
26 pub fn dump(quals: Qualifiers, w: anytype) !void {
27 if (quals.@"const") try w.writeAll("const ");
28 if (quals.atomic) try w.writeAll("_Atomic ");
29 if (quals.@"volatile") try w.writeAll("volatile ");
30 if (quals.restrict) try w.writeAll("restrict ");
31 if (quals.register) try w.writeAll("register ");
32 }
33
34 /// Merge the const/volatile qualifiers, used by type resolution
35 /// of the conditional operator
36 pub fn mergeCV(a: Qualifiers, b: Qualifiers) Qualifiers {
37 return .{
38 .@"const" = a.@"const" or b.@"const",
39 .@"volatile" = a.@"volatile" or b.@"volatile",
40 };
41 }
42
43 /// Merge all qualifiers, used by typeof()
44 fn mergeAll(a: Qualifiers, b: Qualifiers) Qualifiers {
45 return .{
46 .@"const" = a.@"const" or b.@"const",
47 .atomic = a.atomic or b.atomic,
48 .@"volatile" = a.@"volatile" or b.@"volatile",
49 .restrict = a.restrict or b.restrict,
50 .register = a.register or b.register,
51 };
52 }
53
54 /// Checks if a has all the qualifiers of b
55 pub fn hasQuals(a: Qualifiers, b: Qualifiers) bool {
56 if (b.@"const" and !a.@"const") return false;
57 if (b.@"volatile" and !a.@"volatile") return false;
58 if (b.atomic and !a.atomic) return false;
59 return true;
60 }
61
62 /// register is a storage class and not actually a qualifier
63 /// so it is not preserved by typeof()
64 pub fn inheritFromTypeof(quals: Qualifiers) Qualifiers {
65 var res = quals;
66 res.register = false;
67 return res;
68 }
69
70 pub const Builder = struct {
71 @"const": ?TokenIndex = null,
72 atomic: ?TokenIndex = null,
73 @"volatile": ?TokenIndex = null,
74 restrict: ?TokenIndex = null,
75
76 pub fn finish(b: Qualifiers.Builder, p: *Parser, ty: *Type) !void {
77 if (ty.specifier != .pointer and b.restrict != null) {
78 try p.errStr(.restrict_non_pointer, b.restrict.?, try p.typeStr(ty.*));
79 }
80 if (b.atomic) |some| {
81 if (ty.isArray()) try p.errStr(.atomic_array, some, try p.typeStr(ty.*));
82 if (ty.isFunc()) try p.errStr(.atomic_func, some, try p.typeStr(ty.*));
83 if (ty.hasIncompleteSize()) try p.errStr(.atomic_incomplete, some, try p.typeStr(ty.*));
84 }
85
86 if (b.@"const" != null) ty.qual.@"const" = true;
87 if (b.atomic != null) ty.qual.atomic = true;
88 if (b.@"volatile" != null) ty.qual.@"volatile" = true;
89 if (b.restrict != null) ty.qual.restrict = true;
90 }
91 };
92};
93
94// TODO improve memory usage
95pub const Func = struct {
96 return_type: Type,
97 params: []Param,
98
99 pub const Param = struct {
100 ty: Type,
101 name: StringId,
102 name_tok: TokenIndex,
103 };
104
105 fn eql(a: *const Func, b: *const Func, a_spec: Specifier, b_spec: Specifier, comp: *const Compilation) bool {
106 // return type cannot have qualifiers
107 if (!a.return_type.eql(b.return_type, comp, false)) return false;
108 if (a.params.len == 0 and b.params.len == 0) return true;
109
110 if (a.params.len != b.params.len) {
111 if (a_spec == .old_style_func or b_spec == .old_style_func) {
112 const maybe_has_params = if (a_spec == .old_style_func) b else a;
113 for (maybe_has_params.params) |param| {
114 if (param.ty.undergoesDefaultArgPromotion(comp)) return false;
115 }
116 return true;
117 }
118 return false;
119 }
120 if ((a_spec == .func) != (b_spec == .func)) return false;
121 // TODO validate this
122 for (a.params, b.params) |param, b_qual| {
123 var a_unqual = param.ty;
124 a_unqual.qual.@"const" = false;
125 a_unqual.qual.@"volatile" = false;
126 var b_unqual = b_qual.ty;
127 b_unqual.qual.@"const" = false;
128 b_unqual.qual.@"volatile" = false;
129 if (!a_unqual.eql(b_unqual, comp, true)) return false;
130 }
131 return true;
132 }
133};
134
135pub const Array = struct {
136 len: u64,
137 elem: Type,
138};
139
140pub const Expr = struct {
141 node: NodeIndex,
142 ty: Type,
143};
144
145pub const Attributed = struct {
146 attributes: []Attribute,
147 base: Type,
148
149 pub fn create(allocator: std.mem.Allocator, base_ty: Type, attributes: []const Attribute) !*Attributed {
150 const attributed_type = try allocator.create(Attributed);
151 errdefer allocator.destroy(attributed_type);
152 const duped = try allocator.dupe(Attribute, attributes);
153
154 attributed_type.* = .{
155 .attributes = duped,
156 .base = base_ty,
157 };
158 return attributed_type;
159 }
160};
161
162// TODO improve memory usage
163pub const Enum = struct {
164 fields: []Field,
165 tag_ty: Type,
166 name: StringId,
167 fixed: bool,
168
169 pub const Field = struct {
170 ty: Type,
171 name: StringId,
172 name_tok: TokenIndex,
173 node: NodeIndex,
174 };
175
176 pub fn isIncomplete(e: Enum) bool {
177 return e.fields.len == std.math.maxInt(usize);
178 }
179
180 pub fn create(allocator: std.mem.Allocator, name: StringId, fixed_ty: ?Type) !*Enum {
181 var e = try allocator.create(Enum);
182 e.name = name;
183 e.fields.len = std.math.maxInt(usize);
184 if (fixed_ty) |some| e.tag_ty = some;
185 e.fixed = fixed_ty != null;
186 return e;
187 }
188};
189
190pub const TypeLayout = struct {
191 /// The size of the type in bits.
192 ///
193 /// This is the value returned by `sizeof` in C
194 /// (but in bits instead of bytes). This is a multiple of `pointer_alignment_bits`.
195 size_bits: u64,
196 /// The alignment of the type, in bits, when used as a field in a record.
197 ///
198 /// This is usually the value returned by `_Alignof` in C, but there are some edge
199 /// cases in GCC where `_Alignof` returns a smaller value.
200 field_alignment_bits: u32,
201 /// The alignment, in bits, of valid pointers to this type.
202 /// `size_bits` is a multiple of this value.
203 pointer_alignment_bits: u32,
204 /// The required alignment of the type in bits.
205 ///
206 /// This value is only used by MSVC targets. It is 8 on all other
207 /// targets. On MSVC targets, this value restricts the effects of `#pragma pack` except
208 /// in some cases involving bit-fields.
209 required_alignment_bits: u32,
210};
211
212pub const FieldLayout = struct {
213 /// `offset_bits` and `size_bits` should both be INVALID if and only if the field
214 /// is an unnamed bitfield. There is no way to reference an unnamed bitfield in C, so
215 /// there should be no way to observe these values. If it is used, this value will
216 /// maximize the chance that a safety-checked overflow will occur.
217 const INVALID = std.math.maxInt(u64);
218
219 /// The offset of the field, in bits, from the start of the struct.
220 offset_bits: u64 = INVALID,
221 /// The size, in bits, of the field.
222 ///
223 /// For bit-fields, this is the width of the field.
224 size_bits: u64 = INVALID,
225
226 pub fn isUnnamed(self: FieldLayout) bool {
227 return self.offset_bits == INVALID and self.size_bits == INVALID;
228 }
229};
230
231// TODO improve memory usage
232pub const Record = struct {
233 fields: []Field,
234 type_layout: TypeLayout,
235 /// If this is null, none of the fields have attributes
236 /// Otherwise, it's a pointer to N items (where N == number of fields)
237 /// and the item at index i is the attributes for the field at index i
238 field_attributes: ?[*][]const Attribute,
239 name: StringId,
240
241 pub const Field = struct {
242 ty: Type,
243 name: StringId,
244 /// zero for anonymous fields
245 name_tok: TokenIndex = 0,
246 bit_width: ?u32 = null,
247 layout: FieldLayout = .{
248 .offset_bits = 0,
249 .size_bits = 0,
250 },
251
252 pub fn isNamed(f: *const Field) bool {
253 return f.name_tok != 0;
254 }
255
256 pub fn isAnonymousRecord(f: Field) bool {
257 return !f.isNamed() and f.ty.isRecord();
258 }
259
260 /// false for bitfields
261 pub fn isRegularField(f: *const Field) bool {
262 return f.bit_width == null;
263 }
264
265 /// bit width as specified in the C source. Asserts that `f` is a bitfield.
266 pub fn specifiedBitWidth(f: *const Field) u32 {
267 return f.bit_width.?;
268 }
269 };
270
271 pub fn isIncomplete(r: Record) bool {
272 return r.fields.len == std.math.maxInt(usize);
273 }
274
275 pub fn create(allocator: std.mem.Allocator, name: StringId) !*Record {
276 var r = try allocator.create(Record);
277 r.name = name;
278 r.fields.len = std.math.maxInt(usize);
279 r.field_attributes = null;
280 r.type_layout = .{
281 .size_bits = 8,
282 .field_alignment_bits = 8,
283 .pointer_alignment_bits = 8,
284 .required_alignment_bits = 8,
285 };
286 return r;
287 }
288
289 pub fn hasFieldOfType(self: *const Record, ty: Type, comp: *const Compilation) bool {
290 if (self.isIncomplete()) return false;
291 for (self.fields) |f| {
292 if (ty.eql(f.ty, comp, false)) return true;
293 }
294 return false;
295 }
296
297 pub fn hasField(self: *const Record, name: StringId) bool {
298 std.debug.assert(!self.isIncomplete());
299 for (self.fields) |f| {
300 if (f.isAnonymousRecord() and f.ty.getRecord().?.hasField(name)) return true;
301 if (name == f.name) return true;
302 }
303 return false;
304 }
305};
306
307pub const Specifier = enum {
308 /// A NaN-like poison value
309 invalid,
310
311 /// GNU auto type
312 /// This is a placeholder specifier - it must be replaced by the actual type specifier (determined by the initializer)
313 auto_type,
314 /// C23 auto, behaves like auto_type
315 c23_auto,
316
317 void,
318 bool,
319
320 // integers
321 char,
322 schar,
323 uchar,
324 short,
325 ushort,
326 int,
327 uint,
328 long,
329 ulong,
330 long_long,
331 ulong_long,
332 int128,
333 uint128,
334 complex_char,
335 complex_schar,
336 complex_uchar,
337 complex_short,
338 complex_ushort,
339 complex_int,
340 complex_uint,
341 complex_long,
342 complex_ulong,
343 complex_long_long,
344 complex_ulong_long,
345 complex_int128,
346 complex_uint128,
347
348 // data.int
349 bit_int,
350 complex_bit_int,
351
352 // floating point numbers
353 fp16,
354 float16,
355 float,
356 double,
357 long_double,
358 float128,
359 complex_float16,
360 complex_float,
361 complex_double,
362 complex_long_double,
363 complex_float128,
364
365 // data.sub_type
366 pointer,
367 unspecified_variable_len_array,
368 // data.func
369 /// int foo(int bar, char baz) and int (void)
370 func,
371 /// int foo(int bar, char baz, ...)
372 var_args_func,
373 /// int foo(bar, baz) and int foo()
374 /// is also var args, but we can give warnings about incorrect amounts of parameters
375 old_style_func,
376
377 // data.array
378 array,
379 static_array,
380 incomplete_array,
381 vector,
382 // data.expr
383 variable_len_array,
384
385 // data.record
386 @"struct",
387 @"union",
388
389 // data.enum
390 @"enum",
391
392 /// typeof(type-name)
393 typeof_type,
394
395 /// typeof(expression)
396 typeof_expr,
397
398 /// data.attributed
399 attributed,
400
401 /// C23 nullptr_t
402 nullptr_t,
403};
404
405const Type = @This();
406
407/// All fields of Type except data may be mutated
408data: union {
409 sub_type: *Type,
410 func: *Func,
411 array: *Array,
412 expr: *Expr,
413 @"enum": *Enum,
414 record: *Record,
415 attributed: *Attributed,
416 none: void,
417 int: struct {
418 bits: u16,
419 signedness: std.builtin.Signedness,
420 },
421} = .{ .none = {} },
422specifier: Specifier,
423qual: Qualifiers = .{},
424decayed: bool = false,
425/// typedef name, if any
426name: StringId = .empty,
427
428pub const int = Type{ .specifier = .int };
429pub const invalid = Type{ .specifier = .invalid };
430
431/// Determine if type matches the given specifier, recursing into typeof
432/// types if necessary.
433pub fn is(ty: Type, specifier: Specifier) bool {
434 std.debug.assert(specifier != .typeof_type and specifier != .typeof_expr);
435 return ty.get(specifier) != null;
436}
437
438pub fn withAttributes(self: Type, allocator: std.mem.Allocator, attributes: []const Attribute) !Type {
439 if (attributes.len == 0) return self;
440 const attributed_type = try Type.Attributed.create(allocator, self, attributes);
441 return .{ .specifier = .attributed, .data = .{ .attributed = attributed_type }, .decayed = self.decayed };
442}
443
444pub fn isCallable(ty: Type) ?Type {
445 return switch (ty.specifier) {
446 .func, .var_args_func, .old_style_func => ty,
447 .pointer => if (ty.data.sub_type.isFunc()) ty.data.sub_type.* else null,
448 .typeof_type => ty.data.sub_type.isCallable(),
449 .typeof_expr => ty.data.expr.ty.isCallable(),
450 .attributed => ty.data.attributed.base.isCallable(),
451 else => null,
452 };
453}
454
455pub fn isFunc(ty: Type) bool {
456 return switch (ty.specifier) {
457 .func, .var_args_func, .old_style_func => true,
458 .typeof_type => ty.data.sub_type.isFunc(),
459 .typeof_expr => ty.data.expr.ty.isFunc(),
460 .attributed => ty.data.attributed.base.isFunc(),
461 else => false,
462 };
463}
464
465pub fn isArray(ty: Type) bool {
466 return switch (ty.specifier) {
467 .array, .static_array, .incomplete_array, .variable_len_array, .unspecified_variable_len_array => !ty.isDecayed(),
468 .typeof_type => !ty.isDecayed() and ty.data.sub_type.isArray(),
469 .typeof_expr => !ty.isDecayed() and ty.data.expr.ty.isArray(),
470 .attributed => !ty.isDecayed() and ty.data.attributed.base.isArray(),
471 else => false,
472 };
473}
474
475/// Must only be used to set the length of an incomplete array as determined by its initializer
476pub fn setIncompleteArrayLen(ty: *Type, len: u64) void {
477 switch (ty.specifier) {
478 .incomplete_array => {
479 // Modifying .data is exceptionally allowed for .incomplete_array.
480 ty.data.array.len = len;
481 ty.specifier = .array;
482 },
483
484 .typeof_type => ty.data.sub_type.setIncompleteArrayLen(len),
485 .typeof_expr => ty.data.expr.ty.setIncompleteArrayLen(len),
486 .attributed => ty.data.attributed.base.setIncompleteArrayLen(len),
487
488 else => unreachable,
489 }
490}
491
492/// Whether the type is promoted if used as a variadic argument or as an argument to a function with no prototype
493fn undergoesDefaultArgPromotion(ty: Type, comp: *const Compilation) bool {
494 return switch (ty.specifier) {
495 .bool => true,
496 .char, .uchar, .schar => true,
497 .short, .ushort => true,
498 .@"enum" => if (comp.langopts.emulate == .clang) ty.data.@"enum".isIncomplete() else false,
499 .float => true,
500
501 .typeof_type => ty.data.sub_type.undergoesDefaultArgPromotion(comp),
502 .typeof_expr => ty.data.expr.ty.undergoesDefaultArgPromotion(comp),
503 .attributed => ty.data.attributed.base.undergoesDefaultArgPromotion(comp),
504 else => false,
505 };
506}
507
508pub fn isScalar(ty: Type) bool {
509 return ty.isInt() or ty.isScalarNonInt();
510}
511
512/// To avoid calling isInt() twice for allowable loop/if controlling expressions
513pub fn isScalarNonInt(ty: Type) bool {
514 return ty.isFloat() or ty.isPtr() or ty.is(.nullptr_t);
515}
516
517pub fn isDecayed(ty: Type) bool {
518 return ty.decayed;
519}
520
521pub fn isPtr(ty: Type) bool {
522 return switch (ty.specifier) {
523 .pointer => true,
524
525 .array,
526 .static_array,
527 .incomplete_array,
528 .variable_len_array,
529 .unspecified_variable_len_array,
530 => ty.isDecayed(),
531 .typeof_type => ty.isDecayed() or ty.data.sub_type.isPtr(),
532 .typeof_expr => ty.isDecayed() or ty.data.expr.ty.isPtr(),
533 .attributed => ty.isDecayed() or ty.data.attributed.base.isPtr(),
534 else => false,
535 };
536}
537
538pub fn isInt(ty: Type) bool {
539 return switch (ty.specifier) {
540 // zig fmt: off
541 .@"enum", .bool, .char, .schar, .uchar, .short, .ushort, .int, .uint, .long, .ulong,
542 .long_long, .ulong_long, .int128, .uint128, .complex_char, .complex_schar, .complex_uchar,
543 .complex_short, .complex_ushort, .complex_int, .complex_uint, .complex_long, .complex_ulong,
544 .complex_long_long, .complex_ulong_long, .complex_int128, .complex_uint128,
545 .bit_int, .complex_bit_int => true,
546 // zig fmt: on
547 .typeof_type => ty.data.sub_type.isInt(),
548 .typeof_expr => ty.data.expr.ty.isInt(),
549 .attributed => ty.data.attributed.base.isInt(),
550 else => false,
551 };
552}
553
554pub fn isFloat(ty: Type) bool {
555 return switch (ty.specifier) {
556 // zig fmt: off
557 .float, .double, .long_double, .complex_float, .complex_double, .complex_long_double,
558 .fp16, .float16, .float128, .complex_float128, .complex_float16 => true,
559 // zig fmt: on
560 .typeof_type => ty.data.sub_type.isFloat(),
561 .typeof_expr => ty.data.expr.ty.isFloat(),
562 .attributed => ty.data.attributed.base.isFloat(),
563 else => false,
564 };
565}
566
567pub fn isReal(ty: Type) bool {
568 return switch (ty.specifier) {
569 // zig fmt: off
570 .complex_float, .complex_double, .complex_long_double,
571 .complex_float128, .complex_char, .complex_schar, .complex_uchar, .complex_short,
572 .complex_ushort, .complex_int, .complex_uint, .complex_long, .complex_ulong,
573 .complex_long_long, .complex_ulong_long, .complex_int128, .complex_uint128,
574 .complex_bit_int, .complex_float16 => false,
575 // zig fmt: on
576 .typeof_type => ty.data.sub_type.isReal(),
577 .typeof_expr => ty.data.expr.ty.isReal(),
578 .attributed => ty.data.attributed.base.isReal(),
579 else => true,
580 };
581}
582
583pub fn isComplex(ty: Type) bool {
584 return switch (ty.specifier) {
585 // zig fmt: off
586 .complex_float, .complex_double, .complex_long_double,
587 .complex_float128, .complex_char, .complex_schar, .complex_uchar, .complex_short,
588 .complex_ushort, .complex_int, .complex_uint, .complex_long, .complex_ulong,
589 .complex_long_long, .complex_ulong_long, .complex_int128, .complex_uint128,
590 .complex_bit_int, .complex_float16 => true,
591 // zig fmt: on
592 .typeof_type => ty.data.sub_type.isComplex(),
593 .typeof_expr => ty.data.expr.ty.isComplex(),
594 .attributed => ty.data.attributed.base.isComplex(),
595 else => false,
596 };
597}
598
599pub fn isVoidStar(ty: Type) bool {
600 return switch (ty.specifier) {
601 .pointer => ty.data.sub_type.specifier == .void,
602 .typeof_type => ty.data.sub_type.isVoidStar(),
603 .typeof_expr => ty.data.expr.ty.isVoidStar(),
604 .attributed => ty.data.attributed.base.isVoidStar(),
605 else => false,
606 };
607}
608
609pub fn isTypeof(ty: Type) bool {
610 return switch (ty.specifier) {
611 .typeof_type, .typeof_expr => true,
612 else => false,
613 };
614}
615
616pub fn isConst(ty: Type) bool {
617 return switch (ty.specifier) {
618 .typeof_type => ty.qual.@"const" or ty.data.sub_type.isConst(),
619 .typeof_expr => ty.qual.@"const" or ty.data.expr.ty.isConst(),
620 .attributed => ty.data.attributed.base.isConst(),
621 else => ty.qual.@"const",
622 };
623}
624
625pub fn isUnsignedInt(ty: Type, comp: *const Compilation) bool {
626 return ty.signedness(comp) == .unsigned;
627}
628
629pub fn signedness(ty: Type, comp: *const Compilation) std.builtin.Signedness {
630 return switch (ty.specifier) {
631 // zig fmt: off
632 .char, .complex_char => return comp.getCharSignedness(),
633 .uchar, .ushort, .uint, .ulong, .ulong_long, .uint128, .bool, .complex_uchar, .complex_ushort,
634 .complex_uint, .complex_ulong, .complex_ulong_long, .complex_uint128 => .unsigned,
635 // zig fmt: on
636 .bit_int, .complex_bit_int => ty.data.int.signedness,
637 .typeof_type => ty.data.sub_type.signedness(comp),
638 .typeof_expr => ty.data.expr.ty.signedness(comp),
639 .attributed => ty.data.attributed.base.signedness(comp),
640 else => .signed,
641 };
642}
643
644pub fn isEnumOrRecord(ty: Type) bool {
645 return switch (ty.specifier) {
646 .@"enum", .@"struct", .@"union" => true,
647 .typeof_type => ty.data.sub_type.isEnumOrRecord(),
648 .typeof_expr => ty.data.expr.ty.isEnumOrRecord(),
649 .attributed => ty.data.attributed.base.isEnumOrRecord(),
650 else => false,
651 };
652}
653
654pub fn isRecord(ty: Type) bool {
655 return switch (ty.specifier) {
656 .@"struct", .@"union" => true,
657 .typeof_type => ty.data.sub_type.isRecord(),
658 .typeof_expr => ty.data.expr.ty.isRecord(),
659 .attributed => ty.data.attributed.base.isRecord(),
660 else => false,
661 };
662}
663
664pub fn isAnonymousRecord(ty: Type, comp: *const Compilation) bool {
665 return switch (ty.specifier) {
666 // anonymous records can be recognized by their names which are in
667 // the format "(anonymous TAG at path:line:col)".
668 .@"struct", .@"union" => {
669 const mapper = comp.string_interner.getSlowTypeMapper();
670 return mapper.lookup(ty.data.record.name)[0] == '(';
671 },
672 .typeof_type => ty.data.sub_type.isAnonymousRecord(comp),
673 .typeof_expr => ty.data.expr.ty.isAnonymousRecord(comp),
674 .attributed => ty.data.attributed.base.isAnonymousRecord(comp),
675 else => false,
676 };
677}
678
679pub fn elemType(ty: Type) Type {
680 return switch (ty.specifier) {
681 .pointer, .unspecified_variable_len_array => ty.data.sub_type.*,
682 .array, .static_array, .incomplete_array, .vector => ty.data.array.elem,
683 .variable_len_array => ty.data.expr.ty,
684 .typeof_type, .typeof_expr => {
685 const unwrapped = ty.canonicalize(.preserve_quals);
686 var elem = unwrapped.elemType();
687 elem.qual = elem.qual.mergeAll(unwrapped.qual);
688 return elem;
689 },
690 .attributed => ty.data.attributed.base.elemType(),
691 .invalid => Type.invalid,
692 // zig fmt: off
693 .complex_float, .complex_double, .complex_long_double,
694 .complex_float128, .complex_char, .complex_schar, .complex_uchar, .complex_short,
695 .complex_ushort, .complex_int, .complex_uint, .complex_long, .complex_ulong,
696 .complex_long_long, .complex_ulong_long, .complex_int128, .complex_uint128,
697 .complex_bit_int, .complex_float16 => ty.makeReal(),
698 // zig fmt: on
699 else => unreachable,
700 };
701}
702
703pub fn returnType(ty: Type) Type {
704 return switch (ty.specifier) {
705 .func, .var_args_func, .old_style_func => ty.data.func.return_type,
706 .typeof_type => ty.data.sub_type.returnType(),
707 .typeof_expr => ty.data.expr.ty.returnType(),
708 .attributed => ty.data.attributed.base.returnType(),
709 .invalid => Type.invalid,
710 else => unreachable,
711 };
712}
713
714pub fn params(ty: Type) []Func.Param {
715 return switch (ty.specifier) {
716 .func, .var_args_func, .old_style_func => ty.data.func.params,
717 .typeof_type => ty.data.sub_type.params(),
718 .typeof_expr => ty.data.expr.ty.params(),
719 .attributed => ty.data.attributed.base.params(),
720 .invalid => &.{},
721 else => unreachable,
722 };
723}
724
725/// Returns true if the return value or any param of `ty` is `.invalid`
726/// Asserts that ty is a function type
727pub fn isInvalidFunc(ty: Type) bool {
728 if (ty.returnType().is(.invalid)) return true;
729 for (ty.params()) |param| {
730 if (param.ty.is(.invalid)) return true;
731 }
732 return false;
733}
734
735pub fn arrayLen(ty: Type) ?u64 {
736 return switch (ty.specifier) {
737 .array, .static_array => ty.data.array.len,
738 .typeof_type => ty.data.sub_type.arrayLen(),
739 .typeof_expr => ty.data.expr.ty.arrayLen(),
740 .attributed => ty.data.attributed.base.arrayLen(),
741 else => null,
742 };
743}
744
745/// Complex numbers are scalars but they can be initialized with a 2-element initList
746pub fn expectedInitListSize(ty: Type) ?u64 {
747 return if (ty.isComplex()) 2 else ty.arrayLen();
748}
749
750pub fn anyQual(ty: Type) bool {
751 return switch (ty.specifier) {
752 .typeof_type => ty.qual.any() or ty.data.sub_type.anyQual(),
753 .typeof_expr => ty.qual.any() or ty.data.expr.ty.anyQual(),
754 else => ty.qual.any(),
755 };
756}
757
758pub fn getRecord(ty: Type) ?*const Type.Record {
759 return switch (ty.specifier) {
760 .attributed => ty.data.attributed.base.getRecord(),
761 .typeof_type => ty.data.sub_type.getRecord(),
762 .typeof_expr => ty.data.expr.ty.getRecord(),
763 .@"struct", .@"union" => ty.data.record,
764 else => null,
765 };
766}
767
768pub fn compareIntegerRanks(a: Type, b: Type, comp: *const Compilation) std.math.Order {
769 std.debug.assert(a.isInt() and b.isInt());
770 if (a.eql(b, comp, false)) return .eq;
771
772 const a_unsigned = a.isUnsignedInt(comp);
773 const b_unsigned = b.isUnsignedInt(comp);
774
775 const a_rank = a.integerRank(comp);
776 const b_rank = b.integerRank(comp);
777 if (a_unsigned == b_unsigned) {
778 return std.math.order(a_rank, b_rank);
779 }
780 if (a_unsigned) {
781 if (a_rank >= b_rank) return .gt;
782 return .lt;
783 }
784 std.debug.assert(b_unsigned);
785 if (b_rank >= a_rank) return .lt;
786 return .gt;
787}
788
789fn realIntegerConversion(a: Type, b: Type, comp: *const Compilation) Type {
790 std.debug.assert(a.isReal() and b.isReal());
791 const type_order = a.compareIntegerRanks(b, comp);
792 const a_signed = !a.isUnsignedInt(comp);
793 const b_signed = !b.isUnsignedInt(comp);
794 if (a_signed == b_signed) {
795 // If both have the same sign, use higher-rank type.
796 return switch (type_order) {
797 .lt => b,
798 .eq, .gt => a,
799 };
800 } else if (type_order != if (a_signed) std.math.Order.gt else std.math.Order.lt) {
801 // Only one is signed; and the unsigned type has rank >= the signed type
802 // Use the unsigned type
803 return if (b_signed) a else b;
804 } else if (a.bitSizeof(comp).? != b.bitSizeof(comp).?) {
805 // Signed type is higher rank and sizes are not equal
806 // Use the signed type
807 return if (a_signed) a else b;
808 } else {
809 // Signed type is higher rank but same size as unsigned type
810 // e.g. `long` and `unsigned` on x86-linux-gnu
811 // Use unsigned version of the signed type
812 return if (a_signed) a.makeIntegerUnsigned() else b.makeIntegerUnsigned();
813 }
814}
815
816pub fn makeIntegerUnsigned(ty: Type) Type {
817 // TODO discards attributed/typeof
818 var base_ty = ty.canonicalize(.standard);
819 switch (base_ty.specifier) {
820 // zig fmt: off
821 .uchar, .ushort, .uint, .ulong, .ulong_long, .uint128,
822 .complex_uchar, .complex_ushort, .complex_uint, .complex_ulong, .complex_ulong_long, .complex_uint128,
823 => return ty,
824 // zig fmt: on
825
826 .char, .complex_char => {
827 base_ty.specifier = @enumFromInt(@intFromEnum(base_ty.specifier) + 2);
828 return base_ty;
829 },
830
831 // zig fmt: off
832 .schar, .short, .int, .long, .long_long, .int128,
833 .complex_schar, .complex_short, .complex_int, .complex_long, .complex_long_long, .complex_int128 => {
834 base_ty.specifier = @enumFromInt(@intFromEnum(base_ty.specifier) + 1);
835 return base_ty;
836 },
837 // zig fmt: on
838
839 .bit_int, .complex_bit_int => {
840 base_ty.data.int.signedness = .unsigned;
841 return base_ty;
842 },
843 else => unreachable,
844 }
845}
846
847/// Find the common type of a and b for binary operations
848pub fn integerConversion(a: Type, b: Type, comp: *const Compilation) Type {
849 const a_real = a.isReal();
850 const b_real = b.isReal();
851 const target_ty = a.makeReal().realIntegerConversion(b.makeReal(), comp);
852 return if (a_real and b_real) target_ty else target_ty.makeComplex();
853}
854
855pub fn integerPromotion(ty: Type, comp: *Compilation) Type {
856 var specifier = ty.specifier;
857 switch (specifier) {
858 .@"enum" => {
859 if (ty.hasIncompleteSize()) return .{ .specifier = .int };
860 if (ty.data.@"enum".fixed) return ty.data.@"enum".tag_ty.integerPromotion(comp);
861
862 specifier = ty.data.@"enum".tag_ty.specifier;
863 },
864 .bit_int, .complex_bit_int => return .{ .specifier = specifier, .data = ty.data },
865 else => {},
866 }
867 return switch (specifier) {
868 else => .{
869 .specifier = switch (specifier) {
870 // zig fmt: off
871 .bool, .char, .schar, .uchar, .short => .int,
872 .ushort => if (ty.sizeof(comp).? == sizeof(.{ .specifier = .int }, comp)) Specifier.uint else .int,
873 .int, .uint, .long, .ulong, .long_long, .ulong_long, .int128, .uint128, .complex_char,
874 .complex_schar, .complex_uchar, .complex_short, .complex_ushort, .complex_int,
875 .complex_uint, .complex_long, .complex_ulong, .complex_long_long, .complex_ulong_long,
876 .complex_int128, .complex_uint128 => specifier,
877 // zig fmt: on
878 .typeof_type => return ty.data.sub_type.integerPromotion(comp),
879 .typeof_expr => return ty.data.expr.ty.integerPromotion(comp),
880 .attributed => return ty.data.attributed.base.integerPromotion(comp),
881 .invalid => .invalid,
882 else => unreachable, // _BitInt, or not an integer type
883 },
884 },
885 };
886}
887
888/// Promote a bitfield. If `int` can hold all the values of the underlying field,
889/// promote to int. Otherwise, promote to unsigned int
890/// Returns null if no promotion is necessary
891pub fn bitfieldPromotion(ty: Type, comp: *Compilation, width: u32) ?Type {
892 const type_size_bits = ty.bitSizeof(comp).?;
893
894 // Note: GCC and clang will promote `long: 3` to int even though the C standard does not allow this
895 if (width < type_size_bits) {
896 return int;
897 }
898
899 if (width == type_size_bits) {
900 return if (ty.isUnsignedInt(comp)) .{ .specifier = .uint } else int;
901 }
902
903 return null;
904}
905
906pub fn hasIncompleteSize(ty: Type) bool {
907 if (ty.isDecayed()) return false;
908 return switch (ty.specifier) {
909 .void, .incomplete_array => true,
910 .@"enum" => ty.data.@"enum".isIncomplete() and !ty.data.@"enum".fixed,
911 .@"struct", .@"union" => ty.data.record.isIncomplete(),
912 .array, .static_array => ty.data.array.elem.hasIncompleteSize(),
913 .typeof_type => ty.data.sub_type.hasIncompleteSize(),
914 .typeof_expr, .variable_len_array => ty.data.expr.ty.hasIncompleteSize(),
915 .unspecified_variable_len_array => ty.data.sub_type.hasIncompleteSize(),
916 .attributed => ty.data.attributed.base.hasIncompleteSize(),
917 else => false,
918 };
919}
920
921pub fn hasUnboundVLA(ty: Type) bool {
922 var cur = ty;
923 while (true) {
924 switch (cur.specifier) {
925 .unspecified_variable_len_array => return true,
926 .array,
927 .static_array,
928 .incomplete_array,
929 .variable_len_array,
930 => cur = cur.elemType(),
931 .typeof_type => cur = cur.data.sub_type.*,
932 .typeof_expr => cur = cur.data.expr.ty,
933 .attributed => cur = cur.data.attributed.base,
934 else => return false,
935 }
936 }
937}
938
939pub fn hasField(ty: Type, name: StringId) bool {
940 return ty.getRecord().?.hasField(name);
941}
942
943const TypeSizeOrder = enum {
944 lt,
945 gt,
946 eq,
947 indeterminate,
948};
949
950pub fn sizeCompare(a: Type, b: Type, comp: *Compilation) TypeSizeOrder {
951 const a_size = a.sizeof(comp) orelse return .indeterminate;
952 const b_size = b.sizeof(comp) orelse return .indeterminate;
953 return switch (std.math.order(a_size, b_size)) {
954 .lt => .lt,
955 .gt => .gt,
956 .eq => .eq,
957 };
958}
959
960/// Size of type as reported by sizeof
961pub fn sizeof(ty: Type, comp: *const Compilation) ?u64 {
962 if (ty.isPtr()) return comp.target.ptrBitWidth() / 8;
963
964 return switch (ty.specifier) {
965 .auto_type, .c23_auto => unreachable,
966 .variable_len_array, .unspecified_variable_len_array => null,
967 .incomplete_array => return if (comp.langopts.emulate == .msvc) @as(?u64, 0) else null,
968 .func, .var_args_func, .old_style_func, .void, .bool => 1,
969 .char, .schar, .uchar => 1,
970 .short => comp.target.cTypeByteSize(.short),
971 .ushort => comp.target.cTypeByteSize(.ushort),
972 .int => comp.target.cTypeByteSize(.int),
973 .uint => comp.target.cTypeByteSize(.uint),
974 .long => comp.target.cTypeByteSize(.long),
975 .ulong => comp.target.cTypeByteSize(.ulong),
976 .long_long => comp.target.cTypeByteSize(.longlong),
977 .ulong_long => comp.target.cTypeByteSize(.ulonglong),
978 .long_double => comp.target.cTypeByteSize(.longdouble),
979 .int128, .uint128 => 16,
980 .fp16, .float16 => 2,
981 .float => comp.target.cTypeByteSize(.float),
982 .double => comp.target.cTypeByteSize(.double),
983 .float128 => 16,
984 .bit_int => {
985 return std.mem.alignForward(u64, (@as(u32, ty.data.int.bits) + 7) / 8, ty.alignof(comp));
986 },
987 // zig fmt: off
988 .complex_char, .complex_schar, .complex_uchar, .complex_short, .complex_ushort, .complex_int,
989 .complex_uint, .complex_long, .complex_ulong, .complex_long_long, .complex_ulong_long,
990 .complex_int128, .complex_uint128, .complex_float, .complex_double,
991 .complex_long_double, .complex_float128, .complex_bit_int, .complex_float16,
992 => return 2 * ty.makeReal().sizeof(comp).?,
993 // zig fmt: on
994 .pointer => unreachable,
995 .static_array,
996 .nullptr_t,
997 => comp.target.ptrBitWidth() / 8,
998 .array, .vector => {
999 const size = ty.data.array.elem.sizeof(comp) orelse return null;
1000 const arr_size = size * ty.data.array.len;
1001 if (comp.langopts.emulate == .msvc) {
1002 // msvc ignores array type alignment.
1003 // Since the size might not be a multiple of the field
1004 // alignment, the address of the second element might not be properly aligned
1005 // for the field alignment. A flexible array has size 0. See test case 0018.
1006 return arr_size;
1007 } else {
1008 return std.mem.alignForward(u64, arr_size, ty.alignof(comp));
1009 }
1010 },
1011 .@"struct", .@"union" => if (ty.data.record.isIncomplete()) null else @as(u64, ty.data.record.type_layout.size_bits / 8),
1012 .@"enum" => if (ty.data.@"enum".isIncomplete() and !ty.data.@"enum".fixed) null else ty.data.@"enum".tag_ty.sizeof(comp),
1013 .typeof_type => ty.data.sub_type.sizeof(comp),
1014 .typeof_expr => ty.data.expr.ty.sizeof(comp),
1015 .attributed => ty.data.attributed.base.sizeof(comp),
1016 .invalid => return null,
1017 };
1018}
1019
1020pub fn bitSizeof(ty: Type, comp: *const Compilation) ?u64 {
1021 return switch (ty.specifier) {
1022 .bool => if (comp.langopts.emulate == .msvc) @as(u64, 8) else 1,
1023 .typeof_type => ty.data.sub_type.bitSizeof(comp),
1024 .typeof_expr => ty.data.expr.ty.bitSizeof(comp),
1025 .attributed => ty.data.attributed.base.bitSizeof(comp),
1026 .bit_int => return ty.data.int.bits,
1027 .long_double => comp.target.cTypeBitSize(.longdouble),
1028 else => 8 * (ty.sizeof(comp) orelse return null),
1029 };
1030}
1031
1032pub fn alignable(ty: Type) bool {
1033 return (ty.isArray() or !ty.hasIncompleteSize() or ty.is(.void)) and !ty.is(.invalid);
1034}
1035
1036/// Get the alignment of a type
1037pub fn alignof(ty: Type, comp: *const Compilation) u29 {
1038 // don't return the attribute for records
1039 // layout has already accounted for requested alignment
1040 if (ty.requestedAlignment(comp)) |requested| {
1041 // gcc does not respect alignment on enums
1042 if (ty.get(.@"enum")) |ty_enum| {
1043 if (comp.langopts.emulate == .gcc) {
1044 return ty_enum.alignof(comp);
1045 }
1046 } else if (ty.getRecord()) |rec| {
1047 if (ty.hasIncompleteSize()) return 0;
1048 const computed: u29 = @intCast(@divExact(rec.type_layout.field_alignment_bits, 8));
1049 return @max(requested, computed);
1050 } else if (comp.langopts.emulate == .msvc) {
1051 const type_align = ty.data.attributed.base.alignof(comp);
1052 return @max(requested, type_align);
1053 }
1054 return requested;
1055 }
1056
1057 return switch (ty.specifier) {
1058 .invalid => unreachable,
1059 .auto_type, .c23_auto => unreachable,
1060
1061 .variable_len_array,
1062 .incomplete_array,
1063 .unspecified_variable_len_array,
1064 .array,
1065 .vector,
1066 => if (ty.isPtr()) switch (comp.target.cpu.arch) {
1067 .avr => 1,
1068 else => comp.target.ptrBitWidth() / 8,
1069 } else ty.elemType().alignof(comp),
1070 .func, .var_args_func, .old_style_func => target_util.defaultFunctionAlignment(comp.target),
1071 .char, .schar, .uchar, .void, .bool => 1,
1072
1073 // zig fmt: off
1074 .complex_char, .complex_schar, .complex_uchar, .complex_short, .complex_ushort, .complex_int,
1075 .complex_uint, .complex_long, .complex_ulong, .complex_long_long, .complex_ulong_long,
1076 .complex_int128, .complex_uint128, .complex_float, .complex_double,
1077 .complex_long_double, .complex_float128, .complex_bit_int, .complex_float16,
1078 => return ty.makeReal().alignof(comp),
1079 // zig fmt: on
1080
1081 .short => comp.target.cTypeAlignment(.short),
1082 .ushort => comp.target.cTypeAlignment(.ushort),
1083 .int => comp.target.cTypeAlignment(.int),
1084 .uint => comp.target.cTypeAlignment(.uint),
1085
1086 .long => comp.target.cTypeAlignment(.long),
1087 .ulong => comp.target.cTypeAlignment(.ulong),
1088 .long_long => comp.target.cTypeAlignment(.longlong),
1089 .ulong_long => comp.target.cTypeAlignment(.ulonglong),
1090
1091 .bit_int => {
1092 // https://www.open-std.org/jtc1/sc22/wg14/www/docs/n2709.pdf
1093 // _BitInt(N) types align with existing calling conventions. They have the same size and alignment as the
1094 // smallest basic type that can contain them. Types that are larger than __int64_t are conceptually treated
1095 // as struct of register size chunks. The number of chunks is the smallest number that can contain the type.
1096 if (ty.data.int.bits > 64) return 8;
1097 const basic_type = comp.intLeastN(ty.data.int.bits, ty.data.int.signedness);
1098 return basic_type.alignof(comp);
1099 },
1100
1101 .float => comp.target.cTypeAlignment(.float),
1102 .double => comp.target.cTypeAlignment(.double),
1103 .long_double => comp.target.cTypeAlignment(.longdouble),
1104
1105 .int128, .uint128 => if (comp.target.cpu.arch == .s390x and comp.target.os.tag == .linux and comp.target.isGnu()) 8 else 16,
1106 .fp16, .float16 => 2,
1107
1108 .float128 => 16,
1109 .pointer,
1110 .static_array,
1111 .nullptr_t,
1112 => switch (comp.target.cpu.arch) {
1113 .avr => 1,
1114 else => comp.target.ptrBitWidth() / 8,
1115 },
1116 .@"struct", .@"union" => if (ty.data.record.isIncomplete()) 0 else @intCast(ty.data.record.type_layout.field_alignment_bits / 8),
1117 .@"enum" => if (ty.data.@"enum".isIncomplete() and !ty.data.@"enum".fixed) 0 else ty.data.@"enum".tag_ty.alignof(comp),
1118 .typeof_type => ty.data.sub_type.alignof(comp),
1119 .typeof_expr => ty.data.expr.ty.alignof(comp),
1120 .attributed => ty.data.attributed.base.alignof(comp),
1121 };
1122}
1123
1124// This enum should be kept public because it is used by the downstream zig translate-c
1125pub const QualHandling = enum {
1126 standard,
1127 preserve_quals,
1128};
1129
1130/// Canonicalize a possibly-typeof() type. If the type is not a typeof() type, simply
1131/// return it. Otherwise, determine the actual qualified type.
1132/// The `qual_handling` parameter can be used to return the full set of qualifiers
1133/// added by typeof() operations, which is useful when determining the elemType of
1134/// arrays and pointers.
1135pub fn canonicalize(ty: Type, qual_handling: QualHandling) Type {
1136 var cur = ty;
1137 var qual = cur.qual;
1138 while (true) {
1139 switch (cur.specifier) {
1140 .typeof_type => cur = cur.data.sub_type.*,
1141 .typeof_expr => cur = cur.data.expr.ty,
1142 .attributed => cur = cur.data.attributed.base,
1143 else => break,
1144 }
1145 qual = qual.mergeAll(cur.qual);
1146 }
1147 if ((cur.isArray() or cur.isPtr()) and qual_handling == .standard) {
1148 cur.qual = .{};
1149 } else {
1150 cur.qual = qual;
1151 }
1152 cur.decayed = ty.decayed;
1153 return cur;
1154}
1155
1156pub fn get(ty: *const Type, specifier: Specifier) ?*const Type {
1157 std.debug.assert(specifier != .typeof_type and specifier != .typeof_expr);
1158 return switch (ty.specifier) {
1159 .typeof_type => ty.data.sub_type.get(specifier),
1160 .typeof_expr => ty.data.expr.ty.get(specifier),
1161 .attributed => ty.data.attributed.base.get(specifier),
1162 else => if (ty.specifier == specifier) ty else null,
1163 };
1164}
1165
1166pub fn requestedAlignment(ty: Type, comp: *const Compilation) ?u29 {
1167 return switch (ty.specifier) {
1168 .typeof_type => ty.data.sub_type.requestedAlignment(comp),
1169 .typeof_expr => ty.data.expr.ty.requestedAlignment(comp),
1170 .attributed => annotationAlignment(comp, Attribute.Iterator.initType(ty)),
1171 else => null,
1172 };
1173}
1174
1175pub fn enumIsPacked(ty: Type, comp: *const Compilation) bool {
1176 std.debug.assert(ty.is(.@"enum"));
1177 return comp.langopts.short_enums or target_util.packAllEnums(comp.target) or ty.hasAttribute(.@"packed");
1178}
1179
1180pub fn getName(ty: Type) StringId {
1181 return switch (ty.specifier) {
1182 .typeof_type => if (ty.name == .empty) ty.data.sub_type.getName() else ty.name,
1183 .typeof_expr => if (ty.name == .empty) ty.data.expr.ty.getName() else ty.name,
1184 .attributed => if (ty.name == .empty) ty.data.attributed.base.getName() else ty.name,
1185 else => ty.name,
1186 };
1187}
1188
1189pub fn annotationAlignment(comp: *const Compilation, attrs: Attribute.Iterator) ?u29 {
1190 var it = attrs;
1191 var max_requested: ?u29 = null;
1192 var last_aligned_index: ?usize = null;
1193 while (it.next()) |item| {
1194 const attribute, const index = item;
1195 if (attribute.tag != .aligned) continue;
1196 if (last_aligned_index) |aligned_index| {
1197 // once we recurse into a new type, after an `aligned` attribute was found, we're done
1198 if (index <= aligned_index) break;
1199 }
1200 last_aligned_index = index;
1201 const requested = if (attribute.args.aligned.alignment) |alignment| alignment.requested else target_util.defaultAlignment(comp.target);
1202 if (max_requested == null or max_requested.? < requested) {
1203 max_requested = requested;
1204 }
1205 }
1206 return max_requested;
1207}
1208
1209pub fn eql(a_param: Type, b_param: Type, comp: *const Compilation, check_qualifiers: bool) bool {
1210 const a = a_param.canonicalize(.standard);
1211 const b = b_param.canonicalize(.standard);
1212
1213 if (a.specifier == .invalid or b.specifier == .invalid) return false;
1214 if (a.alignof(comp) != b.alignof(comp)) return false;
1215 if (a.isPtr()) {
1216 if (!b.isPtr()) return false;
1217 } else if (a.isFunc()) {
1218 if (!b.isFunc()) return false;
1219 } else if (a.isArray()) {
1220 if (!b.isArray()) return false;
1221 } else if (a.specifier == .@"enum" and b.specifier != .@"enum") {
1222 return a.data.@"enum".tag_ty.eql(b, comp, check_qualifiers);
1223 } else if (b.specifier == .@"enum" and a.specifier != .@"enum") {
1224 return a.eql(b.data.@"enum".tag_ty, comp, check_qualifiers);
1225 } else if (a.specifier != b.specifier) return false;
1226
1227 if (a.qual.atomic != b.qual.atomic) return false;
1228 if (check_qualifiers) {
1229 if (a.qual.@"const" != b.qual.@"const") return false;
1230 if (a.qual.@"volatile" != b.qual.@"volatile") return false;
1231 }
1232
1233 if (a.isPtr()) {
1234 return a_param.elemType().eql(b_param.elemType(), comp, check_qualifiers);
1235 }
1236 switch (a.specifier) {
1237 .pointer => unreachable,
1238
1239 .func,
1240 .var_args_func,
1241 .old_style_func,
1242 => if (!a.data.func.eql(b.data.func, a.specifier, b.specifier, comp)) return false,
1243
1244 .array,
1245 .static_array,
1246 .incomplete_array,
1247 .vector,
1248 => {
1249 const a_len = a.arrayLen();
1250 const b_len = b.arrayLen();
1251 if (a_len == null or b_len == null) {
1252 // At least one array is incomplete; only check child type for equality
1253 } else if (a_len.? != b_len.?) {
1254 return false;
1255 }
1256 if (!a.elemType().eql(b.elemType(), comp, false)) return false;
1257 },
1258 .variable_len_array => {
1259 if (!a.elemType().eql(b.elemType(), comp, check_qualifiers)) return false;
1260 },
1261 .@"struct", .@"union" => if (a.data.record != b.data.record) return false,
1262 .@"enum" => if (a.data.@"enum" != b.data.@"enum") return false,
1263 .bit_int, .complex_bit_int => return a.data.int.bits == b.data.int.bits and a.data.int.signedness == b.data.int.signedness,
1264
1265 else => {},
1266 }
1267 return true;
1268}
1269
1270/// Decays an array to a pointer
1271pub fn decayArray(ty: *Type) void {
1272 std.debug.assert(ty.isArray());
1273 ty.decayed = true;
1274}
1275
1276pub fn originalTypeOfDecayedArray(ty: Type) Type {
1277 std.debug.assert(ty.isDecayed());
1278 var copy = ty;
1279 copy.decayed = false;
1280 return copy;
1281}
1282
1283/// Rank for floating point conversions, ignoring domain (complex vs real)
1284/// Asserts that ty is a floating point type
1285pub fn floatRank(ty: Type) usize {
1286 const real = ty.makeReal();
1287 return switch (real.specifier) {
1288 // TODO: bfloat16 => 0
1289 .float16 => 1,
1290 .fp16 => 2,
1291 .float => 3,
1292 .double => 4,
1293 .long_double => 5,
1294 .float128 => 6,
1295 // TODO: ibm128 => 7
1296 else => unreachable,
1297 };
1298}
1299
1300/// Rank for integer conversions, ignoring domain (complex vs real)
1301/// Asserts that ty is an integer type
1302pub fn integerRank(ty: Type, comp: *const Compilation) usize {
1303 const real = ty.makeReal();
1304 return @intCast(switch (real.specifier) {
1305 .bit_int => @as(u64, real.data.int.bits) << 3,
1306
1307 .bool => 1 + (ty.bitSizeof(comp).? << 3),
1308 .char, .schar, .uchar => 2 + (ty.bitSizeof(comp).? << 3),
1309 .short, .ushort => 3 + (ty.bitSizeof(comp).? << 3),
1310 .int, .uint => 4 + (ty.bitSizeof(comp).? << 3),
1311 .long, .ulong => 5 + (ty.bitSizeof(comp).? << 3),
1312 .long_long, .ulong_long => 6 + (ty.bitSizeof(comp).? << 3),
1313 .int128, .uint128 => 7 + (ty.bitSizeof(comp).? << 3),
1314
1315 .typeof_type => ty.data.sub_type.integerRank(comp),
1316 .typeof_expr => ty.data.expr.ty.integerRank(comp),
1317 .attributed => ty.data.attributed.base.integerRank(comp),
1318
1319 .@"enum" => real.data.@"enum".tag_ty.integerRank(comp),
1320
1321 else => unreachable,
1322 });
1323}
1324
1325/// Returns true if `a` and `b` are integer types that differ only in sign
1326pub fn sameRankDifferentSign(a: Type, b: Type, comp: *const Compilation) bool {
1327 if (!a.isInt() or !b.isInt()) return false;
1328 if (a.hasIncompleteSize() or b.hasIncompleteSize()) return false;
1329 if (a.integerRank(comp) != b.integerRank(comp)) return false;
1330 return a.isUnsignedInt(comp) != b.isUnsignedInt(comp);
1331}
1332
1333pub fn makeReal(ty: Type) Type {
1334 // TODO discards attributed/typeof
1335 var base_ty = ty.canonicalize(.standard);
1336 switch (base_ty.specifier) {
1337 .complex_float16, .complex_float, .complex_double, .complex_long_double, .complex_float128 => {
1338 base_ty.specifier = @enumFromInt(@intFromEnum(base_ty.specifier) - 5);
1339 return base_ty;
1340 },
1341 .complex_char, .complex_schar, .complex_uchar, .complex_short, .complex_ushort, .complex_int, .complex_uint, .complex_long, .complex_ulong, .complex_long_long, .complex_ulong_long, .complex_int128, .complex_uint128 => {
1342 base_ty.specifier = @enumFromInt(@intFromEnum(base_ty.specifier) - 13);
1343 return base_ty;
1344 },
1345 .complex_bit_int => {
1346 base_ty.specifier = .bit_int;
1347 return base_ty;
1348 },
1349 else => return ty,
1350 }
1351}
1352
1353pub fn makeComplex(ty: Type) Type {
1354 // TODO discards attributed/typeof
1355 var base_ty = ty.canonicalize(.standard);
1356 switch (base_ty.specifier) {
1357 .float, .double, .long_double, .float128 => {
1358 base_ty.specifier = @enumFromInt(@intFromEnum(base_ty.specifier) + 5);
1359 return base_ty;
1360 },
1361 .char, .schar, .uchar, .short, .ushort, .int, .uint, .long, .ulong, .long_long, .ulong_long, .int128, .uint128 => {
1362 base_ty.specifier = @enumFromInt(@intFromEnum(base_ty.specifier) + 13);
1363 return base_ty;
1364 },
1365 .bit_int => {
1366 base_ty.specifier = .complex_bit_int;
1367 return base_ty;
1368 },
1369 else => return ty,
1370 }
1371}
1372
1373/// Combines types recursively in the order they were parsed, uses `.void` specifier as a sentinel value.
1374pub fn combine(inner: *Type, outer: Type) Parser.Error!void {
1375 switch (inner.specifier) {
1376 .pointer => return inner.data.sub_type.combine(outer),
1377 .unspecified_variable_len_array => {
1378 std.debug.assert(!inner.isDecayed());
1379 try inner.data.sub_type.combine(outer);
1380 },
1381 .variable_len_array => {
1382 std.debug.assert(!inner.isDecayed());
1383 try inner.data.expr.ty.combine(outer);
1384 },
1385 .array, .static_array, .incomplete_array => {
1386 std.debug.assert(!inner.isDecayed());
1387 try inner.data.array.elem.combine(outer);
1388 },
1389 .func, .var_args_func, .old_style_func => {
1390 try inner.data.func.return_type.combine(outer);
1391 },
1392 .typeof_type,
1393 .typeof_expr,
1394 => std.debug.assert(!inner.isDecayed()),
1395 .void, .invalid => inner.* = outer,
1396 else => unreachable,
1397 }
1398}
1399
1400pub fn validateCombinedType(ty: Type, p: *Parser, source_tok: TokenIndex) Parser.Error!void {
1401 switch (ty.specifier) {
1402 .pointer => return ty.data.sub_type.validateCombinedType(p, source_tok),
1403 .unspecified_variable_len_array,
1404 .variable_len_array,
1405 .array,
1406 .static_array,
1407 .incomplete_array,
1408 => {
1409 const elem_ty = ty.elemType();
1410 if (elem_ty.hasIncompleteSize()) {
1411 try p.errStr(.array_incomplete_elem, source_tok, try p.typeStr(elem_ty));
1412 return error.ParsingFailed;
1413 }
1414 if (elem_ty.isFunc()) {
1415 try p.errTok(.array_func_elem, source_tok);
1416 return error.ParsingFailed;
1417 }
1418 if (elem_ty.specifier == .static_array and elem_ty.isArray()) {
1419 try p.errTok(.static_non_outermost_array, source_tok);
1420 }
1421 if (elem_ty.anyQual() and elem_ty.isArray()) {
1422 try p.errTok(.qualifier_non_outermost_array, source_tok);
1423 }
1424 },
1425 .func, .var_args_func, .old_style_func => {
1426 const ret_ty = &ty.data.func.return_type;
1427 if (ret_ty.isArray()) try p.errTok(.func_cannot_return_array, source_tok);
1428 if (ret_ty.isFunc()) try p.errTok(.func_cannot_return_func, source_tok);
1429 if (ret_ty.qual.@"const") {
1430 try p.errStr(.qual_on_ret_type, source_tok, "const");
1431 ret_ty.qual.@"const" = false;
1432 }
1433 if (ret_ty.qual.@"volatile") {
1434 try p.errStr(.qual_on_ret_type, source_tok, "volatile");
1435 ret_ty.qual.@"volatile" = false;
1436 }
1437 if (ret_ty.qual.atomic) {
1438 try p.errStr(.qual_on_ret_type, source_tok, "atomic");
1439 ret_ty.qual.atomic = false;
1440 }
1441 if (ret_ty.is(.fp16) and !p.comp.hasHalfPrecisionFloatABI()) {
1442 try p.errStr(.suggest_pointer_for_invalid_fp16, source_tok, "function return value");
1443 }
1444 },
1445 .typeof_type => return ty.data.sub_type.validateCombinedType(p, source_tok),
1446 .typeof_expr => return ty.data.expr.ty.validateCombinedType(p, source_tok),
1447 .attributed => return ty.data.attributed.base.validateCombinedType(p, source_tok),
1448 else => {},
1449 }
1450}
1451
1452/// An unfinished Type
1453pub const Builder = struct {
1454 complex_tok: ?TokenIndex = null,
1455 bit_int_tok: ?TokenIndex = null,
1456 auto_type_tok: ?TokenIndex = null,
1457 typedef: ?struct {
1458 tok: TokenIndex,
1459 ty: Type,
1460 } = null,
1461 specifier: Builder.Specifier = .none,
1462 qual: Qualifiers.Builder = .{},
1463 typeof: ?Type = null,
1464 /// When true an error is returned instead of adding a diagnostic message.
1465 /// Used for trying to combine typedef types.
1466 error_on_invalid: bool = false,
1467
1468 pub const Specifier = union(enum) {
1469 none,
1470 void,
1471 /// GNU __auto_type extension
1472 auto_type,
1473 /// C23 auto
1474 c23_auto,
1475 nullptr_t,
1476 bool,
1477 char,
1478 schar,
1479 uchar,
1480 complex_char,
1481 complex_schar,
1482 complex_uchar,
1483
1484 unsigned,
1485 signed,
1486 short,
1487 sshort,
1488 ushort,
1489 short_int,
1490 sshort_int,
1491 ushort_int,
1492 int,
1493 sint,
1494 uint,
1495 long,
1496 slong,
1497 ulong,
1498 long_int,
1499 slong_int,
1500 ulong_int,
1501 long_long,
1502 slong_long,
1503 ulong_long,
1504 long_long_int,
1505 slong_long_int,
1506 ulong_long_int,
1507 int128,
1508 sint128,
1509 uint128,
1510 complex_unsigned,
1511 complex_signed,
1512 complex_short,
1513 complex_sshort,
1514 complex_ushort,
1515 complex_short_int,
1516 complex_sshort_int,
1517 complex_ushort_int,
1518 complex_int,
1519 complex_sint,
1520 complex_uint,
1521 complex_long,
1522 complex_slong,
1523 complex_ulong,
1524 complex_long_int,
1525 complex_slong_int,
1526 complex_ulong_int,
1527 complex_long_long,
1528 complex_slong_long,
1529 complex_ulong_long,
1530 complex_long_long_int,
1531 complex_slong_long_int,
1532 complex_ulong_long_int,
1533 complex_int128,
1534 complex_sint128,
1535 complex_uint128,
1536 bit_int: u64,
1537 sbit_int: u64,
1538 ubit_int: u64,
1539 complex_bit_int: u64,
1540 complex_sbit_int: u64,
1541 complex_ubit_int: u64,
1542
1543 fp16,
1544 float16,
1545 float,
1546 double,
1547 long_double,
1548 float128,
1549 complex,
1550 complex_float16,
1551 complex_float,
1552 complex_double,
1553 complex_long_double,
1554 complex_float128,
1555
1556 pointer: *Type,
1557 unspecified_variable_len_array: *Type,
1558 decayed_unspecified_variable_len_array: *Type,
1559 func: *Func,
1560 var_args_func: *Func,
1561 old_style_func: *Func,
1562 array: *Array,
1563 decayed_array: *Array,
1564 static_array: *Array,
1565 decayed_static_array: *Array,
1566 incomplete_array: *Array,
1567 decayed_incomplete_array: *Array,
1568 vector: *Array,
1569 variable_len_array: *Expr,
1570 decayed_variable_len_array: *Expr,
1571 @"struct": *Record,
1572 @"union": *Record,
1573 @"enum": *Enum,
1574 typeof_type: *Type,
1575 decayed_typeof_type: *Type,
1576 typeof_expr: *Expr,
1577 decayed_typeof_expr: *Expr,
1578
1579 attributed: *Attributed,
1580 decayed_attributed: *Attributed,
1581
1582 pub fn str(spec: Builder.Specifier, langopts: LangOpts) ?[]const u8 {
1583 return switch (spec) {
1584 .none => unreachable,
1585 .void => "void",
1586 .auto_type => "__auto_type",
1587 .c23_auto => "auto",
1588 .nullptr_t => "nullptr_t",
1589 .bool => if (langopts.standard.atLeast(.c23)) "bool" else "_Bool",
1590 .char => "char",
1591 .schar => "signed char",
1592 .uchar => "unsigned char",
1593 .unsigned => "unsigned",
1594 .signed => "signed",
1595 .short => "short",
1596 .ushort => "unsigned short",
1597 .sshort => "signed short",
1598 .short_int => "short int",
1599 .sshort_int => "signed short int",
1600 .ushort_int => "unsigned short int",
1601 .int => "int",
1602 .sint => "signed int",
1603 .uint => "unsigned int",
1604 .long => "long",
1605 .slong => "signed long",
1606 .ulong => "unsigned long",
1607 .long_int => "long int",
1608 .slong_int => "signed long int",
1609 .ulong_int => "unsigned long int",
1610 .long_long => "long long",
1611 .slong_long => "signed long long",
1612 .ulong_long => "unsigned long long",
1613 .long_long_int => "long long int",
1614 .slong_long_int => "signed long long int",
1615 .ulong_long_int => "unsigned long long int",
1616 .int128 => "__int128",
1617 .sint128 => "signed __int128",
1618 .uint128 => "unsigned __int128",
1619 .complex_char => "_Complex char",
1620 .complex_schar => "_Complex signed char",
1621 .complex_uchar => "_Complex unsigned char",
1622 .complex_unsigned => "_Complex unsigned",
1623 .complex_signed => "_Complex signed",
1624 .complex_short => "_Complex short",
1625 .complex_ushort => "_Complex unsigned short",
1626 .complex_sshort => "_Complex signed short",
1627 .complex_short_int => "_Complex short int",
1628 .complex_sshort_int => "_Complex signed short int",
1629 .complex_ushort_int => "_Complex unsigned short int",
1630 .complex_int => "_Complex int",
1631 .complex_sint => "_Complex signed int",
1632 .complex_uint => "_Complex unsigned int",
1633 .complex_long => "_Complex long",
1634 .complex_slong => "_Complex signed long",
1635 .complex_ulong => "_Complex unsigned long",
1636 .complex_long_int => "_Complex long int",
1637 .complex_slong_int => "_Complex signed long int",
1638 .complex_ulong_int => "_Complex unsigned long int",
1639 .complex_long_long => "_Complex long long",
1640 .complex_slong_long => "_Complex signed long long",
1641 .complex_ulong_long => "_Complex unsigned long long",
1642 .complex_long_long_int => "_Complex long long int",
1643 .complex_slong_long_int => "_Complex signed long long int",
1644 .complex_ulong_long_int => "_Complex unsigned long long int",
1645 .complex_int128 => "_Complex __int128",
1646 .complex_sint128 => "_Complex signed __int128",
1647 .complex_uint128 => "_Complex unsigned __int128",
1648
1649 .fp16 => "__fp16",
1650 .float16 => "_Float16",
1651 .float => "float",
1652 .double => "double",
1653 .long_double => "long double",
1654 .float128 => "__float128",
1655 .complex => "_Complex",
1656 .complex_float16 => "_Complex _Float16",
1657 .complex_float => "_Complex float",
1658 .complex_double => "_Complex double",
1659 .complex_long_double => "_Complex long double",
1660 .complex_float128 => "_Complex __float128",
1661
1662 .attributed => |attributed| Builder.fromType(attributed.base).str(langopts),
1663
1664 else => null,
1665 };
1666 }
1667 };
1668
1669 pub fn finish(b: Builder, p: *Parser) Parser.Error!Type {
1670 var ty: Type = .{ .specifier = undefined };
1671 if (b.typedef) |typedef| {
1672 ty = typedef.ty;
1673 if (ty.isArray()) {
1674 var elem = ty.elemType();
1675 try b.qual.finish(p, &elem);
1676 // TODO this really should be easier
1677 switch (ty.specifier) {
1678 .array, .static_array, .incomplete_array => {
1679 const old = ty.data.array;
1680 ty.data.array = try p.arena.create(Array);
1681 ty.data.array.* = .{
1682 .len = old.len,
1683 .elem = elem,
1684 };
1685 },
1686 .variable_len_array, .unspecified_variable_len_array => {
1687 const old = ty.data.expr;
1688 ty.data.expr = try p.arena.create(Expr);
1689 ty.data.expr.* = .{
1690 .node = old.node,
1691 .ty = elem,
1692 };
1693 },
1694 .typeof_type => {}, // TODO handle
1695 .typeof_expr => {}, // TODO handle
1696 .attributed => {}, // TODO handle
1697 else => unreachable,
1698 }
1699
1700 return ty;
1701 }
1702 try b.qual.finish(p, &ty);
1703 return ty;
1704 }
1705 switch (b.specifier) {
1706 .none => {
1707 if (b.typeof) |typeof| {
1708 ty = typeof;
1709 } else {
1710 ty.specifier = .int;
1711 if (p.comp.langopts.standard.atLeast(.c23)) {
1712 try p.err(.missing_type_specifier_c23);
1713 } else {
1714 try p.err(.missing_type_specifier);
1715 }
1716 }
1717 },
1718 .void => ty.specifier = .void,
1719 .auto_type => ty.specifier = .auto_type,
1720 .c23_auto => ty.specifier = .c23_auto,
1721 .nullptr_t => unreachable, // nullptr_t can only be accessed via typeof(nullptr)
1722 .bool => ty.specifier = .bool,
1723 .char => ty.specifier = .char,
1724 .schar => ty.specifier = .schar,
1725 .uchar => ty.specifier = .uchar,
1726 .complex_char => ty.specifier = .complex_char,
1727 .complex_schar => ty.specifier = .complex_schar,
1728 .complex_uchar => ty.specifier = .complex_uchar,
1729
1730 .unsigned => ty.specifier = .uint,
1731 .signed => ty.specifier = .int,
1732 .short_int, .sshort_int, .short, .sshort => ty.specifier = .short,
1733 .ushort, .ushort_int => ty.specifier = .ushort,
1734 .int, .sint => ty.specifier = .int,
1735 .uint => ty.specifier = .uint,
1736 .long, .slong, .long_int, .slong_int => ty.specifier = .long,
1737 .ulong, .ulong_int => ty.specifier = .ulong,
1738 .long_long, .slong_long, .long_long_int, .slong_long_int => ty.specifier = .long_long,
1739 .ulong_long, .ulong_long_int => ty.specifier = .ulong_long,
1740 .int128, .sint128 => ty.specifier = .int128,
1741 .uint128 => ty.specifier = .uint128,
1742 .complex_unsigned => ty.specifier = .complex_uint,
1743 .complex_signed => ty.specifier = .complex_int,
1744 .complex_short_int, .complex_sshort_int, .complex_short, .complex_sshort => ty.specifier = .complex_short,
1745 .complex_ushort, .complex_ushort_int => ty.specifier = .complex_ushort,
1746 .complex_int, .complex_sint => ty.specifier = .complex_int,
1747 .complex_uint => ty.specifier = .complex_uint,
1748 .complex_long, .complex_slong, .complex_long_int, .complex_slong_int => ty.specifier = .complex_long,
1749 .complex_ulong, .complex_ulong_int => ty.specifier = .complex_ulong,
1750 .complex_long_long, .complex_slong_long, .complex_long_long_int, .complex_slong_long_int => ty.specifier = .complex_long_long,
1751 .complex_ulong_long, .complex_ulong_long_int => ty.specifier = .complex_ulong_long,
1752 .complex_int128, .complex_sint128 => ty.specifier = .complex_int128,
1753 .complex_uint128 => ty.specifier = .complex_uint128,
1754 .bit_int, .sbit_int, .ubit_int, .complex_bit_int, .complex_ubit_int, .complex_sbit_int => |bits| {
1755 const unsigned = b.specifier == .ubit_int or b.specifier == .complex_ubit_int;
1756 const complex_str = if (b.complex_tok != null) "_Complex " else "";
1757 if (unsigned) {
1758 if (bits < 1) {
1759 try p.errStr(.unsigned_bit_int_too_small, b.bit_int_tok.?, complex_str);
1760 return Type.invalid;
1761 }
1762 } else {
1763 if (bits < 2) {
1764 try p.errStr(.signed_bit_int_too_small, b.bit_int_tok.?, complex_str);
1765 return Type.invalid;
1766 }
1767 }
1768 if (bits > Compilation.bit_int_max_bits) {
1769 try p.errStr(if (unsigned) .unsigned_bit_int_too_big else .signed_bit_int_too_big, b.bit_int_tok.?, complex_str);
1770 return Type.invalid;
1771 }
1772 ty.specifier = if (b.complex_tok != null) .complex_bit_int else .bit_int;
1773 ty.data = .{ .int = .{
1774 .signedness = if (unsigned) .unsigned else .signed,
1775 .bits = @intCast(bits),
1776 } };
1777 },
1778
1779 .fp16 => ty.specifier = .fp16,
1780 .float16 => ty.specifier = .float16,
1781 .float => ty.specifier = .float,
1782 .double => ty.specifier = .double,
1783 .long_double => ty.specifier = .long_double,
1784 .float128 => ty.specifier = .float128,
1785 .complex_float16 => ty.specifier = .complex_float16,
1786 .complex_float => ty.specifier = .complex_float,
1787 .complex_double => ty.specifier = .complex_double,
1788 .complex_long_double => ty.specifier = .complex_long_double,
1789 .complex_float128 => ty.specifier = .complex_float128,
1790 .complex => {
1791 try p.errTok(.plain_complex, p.tok_i - 1);
1792 ty.specifier = .complex_double;
1793 },
1794
1795 .pointer => |data| {
1796 ty.specifier = .pointer;
1797 ty.data = .{ .sub_type = data };
1798 },
1799 .unspecified_variable_len_array, .decayed_unspecified_variable_len_array => |data| {
1800 ty.specifier = .unspecified_variable_len_array;
1801 ty.data = .{ .sub_type = data };
1802 ty.decayed = b.specifier == .decayed_unspecified_variable_len_array;
1803 },
1804 .func => |data| {
1805 ty.specifier = .func;
1806 ty.data = .{ .func = data };
1807 },
1808 .var_args_func => |data| {
1809 ty.specifier = .var_args_func;
1810 ty.data = .{ .func = data };
1811 },
1812 .old_style_func => |data| {
1813 ty.specifier = .old_style_func;
1814 ty.data = .{ .func = data };
1815 },
1816 .array, .decayed_array => |data| {
1817 ty.specifier = .array;
1818 ty.data = .{ .array = data };
1819 ty.decayed = b.specifier == .decayed_array;
1820 },
1821 .static_array, .decayed_static_array => |data| {
1822 ty.specifier = .static_array;
1823 ty.data = .{ .array = data };
1824 ty.decayed = b.specifier == .decayed_static_array;
1825 },
1826 .incomplete_array, .decayed_incomplete_array => |data| {
1827 ty.specifier = .incomplete_array;
1828 ty.data = .{ .array = data };
1829 ty.decayed = b.specifier == .decayed_incomplete_array;
1830 },
1831 .vector => |data| {
1832 ty.specifier = .vector;
1833 ty.data = .{ .array = data };
1834 },
1835 .variable_len_array, .decayed_variable_len_array => |data| {
1836 ty.specifier = .variable_len_array;
1837 ty.data = .{ .expr = data };
1838 ty.decayed = b.specifier == .decayed_variable_len_array;
1839 },
1840 .@"struct" => |data| {
1841 ty.specifier = .@"struct";
1842 ty.data = .{ .record = data };
1843 },
1844 .@"union" => |data| {
1845 ty.specifier = .@"union";
1846 ty.data = .{ .record = data };
1847 },
1848 .@"enum" => |data| {
1849 ty.specifier = .@"enum";
1850 ty.data = .{ .@"enum" = data };
1851 },
1852 .typeof_type, .decayed_typeof_type => |data| {
1853 ty.specifier = .typeof_type;
1854 ty.data = .{ .sub_type = data };
1855 ty.decayed = b.specifier == .decayed_typeof_type;
1856 },
1857 .typeof_expr, .decayed_typeof_expr => |data| {
1858 ty.specifier = .typeof_expr;
1859 ty.data = .{ .expr = data };
1860 ty.decayed = b.specifier == .decayed_typeof_expr;
1861 },
1862 .attributed, .decayed_attributed => |data| {
1863 ty.specifier = .attributed;
1864 ty.data = .{ .attributed = data };
1865 ty.decayed = b.specifier == .decayed_attributed;
1866 },
1867 }
1868 if (!ty.isReal() and ty.isInt()) {
1869 if (b.complex_tok) |tok| try p.errTok(.complex_int, tok);
1870 }
1871 try b.qual.finish(p, &ty);
1872 return ty;
1873 }
1874
1875 fn cannotCombine(b: Builder, p: *Parser, source_tok: TokenIndex) !void {
1876 if (b.error_on_invalid) return error.CannotCombine;
1877 const ty_str = b.specifier.str(p.comp.langopts) orelse try p.typeStr(try b.finish(p));
1878 try p.errExtra(.cannot_combine_spec, source_tok, .{ .str = ty_str });
1879 if (b.typedef) |some| try p.errStr(.spec_from_typedef, some.tok, try p.typeStr(some.ty));
1880 }
1881
1882 fn duplicateSpec(b: *Builder, p: *Parser, source_tok: TokenIndex, spec: []const u8) !void {
1883 if (b.error_on_invalid) return error.CannotCombine;
1884 if (p.comp.langopts.emulate != .clang) return b.cannotCombine(p, source_tok);
1885 try p.errStr(.duplicate_decl_spec, p.tok_i, spec);
1886 }
1887
1888 pub fn combineFromTypeof(b: *Builder, p: *Parser, new: Type, source_tok: TokenIndex) Compilation.Error!void {
1889 if (b.typeof != null) return p.errStr(.cannot_combine_spec, source_tok, "typeof");
1890 if (b.specifier != .none) return p.errStr(.invalid_typeof, source_tok, @tagName(b.specifier));
1891 const inner = switch (new.specifier) {
1892 .typeof_type => new.data.sub_type.*,
1893 .typeof_expr => new.data.expr.ty,
1894 .nullptr_t => new, // typeof(nullptr) is special-cased to be an unwrapped typeof-expr
1895 else => unreachable,
1896 };
1897
1898 b.typeof = switch (inner.specifier) {
1899 .attributed => inner.data.attributed.base,
1900 else => new,
1901 };
1902 }
1903
1904 /// Try to combine type from typedef, returns true if successful.
1905 pub fn combineTypedef(b: *Builder, p: *Parser, typedef_ty: Type, name_tok: TokenIndex) bool {
1906 if (typedef_ty.is(.invalid)) return false;
1907 b.error_on_invalid = true;
1908 defer b.error_on_invalid = false;
1909
1910 const new_spec = fromType(typedef_ty);
1911 b.combineExtra(p, new_spec, 0) catch |err| switch (err) {
1912 error.FatalError => unreachable, // we do not add any diagnostics
1913 error.OutOfMemory => unreachable, // we do not add any diagnostics
1914 error.ParsingFailed => unreachable, // we do not add any diagnostics
1915 error.CannotCombine => return false,
1916 };
1917 b.typedef = .{ .tok = name_tok, .ty = typedef_ty };
1918 return true;
1919 }
1920
1921 pub fn combine(b: *Builder, p: *Parser, new: Builder.Specifier, source_tok: TokenIndex) !void {
1922 b.combineExtra(p, new, source_tok) catch |err| switch (err) {
1923 error.CannotCombine => unreachable,
1924 else => |e| return e,
1925 };
1926 }
1927
1928 fn combineExtra(b: *Builder, p: *Parser, new: Builder.Specifier, source_tok: TokenIndex) !void {
1929 if (b.typeof != null) {
1930 if (b.error_on_invalid) return error.CannotCombine;
1931 try p.errStr(.invalid_typeof, source_tok, @tagName(new));
1932 }
1933
1934 switch (new) {
1935 .complex => b.complex_tok = source_tok,
1936 .bit_int => b.bit_int_tok = source_tok,
1937 .auto_type => b.auto_type_tok = source_tok,
1938 else => {},
1939 }
1940
1941 if (new == .int128 and !target_util.hasInt128(p.comp.target)) {
1942 try p.errStr(.type_not_supported_on_target, source_tok, "__int128");
1943 }
1944
1945 switch (new) {
1946 else => switch (b.specifier) {
1947 .none => b.specifier = new,
1948 else => return b.cannotCombine(p, source_tok),
1949 },
1950 .signed => b.specifier = switch (b.specifier) {
1951 .none => .signed,
1952 .char => .schar,
1953 .short => .sshort,
1954 .short_int => .sshort_int,
1955 .int => .sint,
1956 .long => .slong,
1957 .long_int => .slong_int,
1958 .long_long => .slong_long,
1959 .long_long_int => .slong_long_int,
1960 .int128 => .sint128,
1961 .bit_int => |bits| .{ .sbit_int = bits },
1962 .complex => .complex_signed,
1963 .complex_char => .complex_schar,
1964 .complex_short => .complex_sshort,
1965 .complex_short_int => .complex_sshort_int,
1966 .complex_int => .complex_sint,
1967 .complex_long => .complex_slong,
1968 .complex_long_int => .complex_slong_int,
1969 .complex_long_long => .complex_slong_long,
1970 .complex_long_long_int => .complex_slong_long_int,
1971 .complex_int128 => .complex_sint128,
1972 .complex_bit_int => |bits| .{ .complex_sbit_int = bits },
1973 .signed,
1974 .sshort,
1975 .sshort_int,
1976 .sint,
1977 .slong,
1978 .slong_int,
1979 .slong_long,
1980 .slong_long_int,
1981 .sint128,
1982 .sbit_int,
1983 .complex_schar,
1984 .complex_signed,
1985 .complex_sshort,
1986 .complex_sshort_int,
1987 .complex_sint,
1988 .complex_slong,
1989 .complex_slong_int,
1990 .complex_slong_long,
1991 .complex_slong_long_int,
1992 .complex_sint128,
1993 .complex_sbit_int,
1994 => return b.duplicateSpec(p, source_tok, "signed"),
1995 else => return b.cannotCombine(p, source_tok),
1996 },
1997 .unsigned => b.specifier = switch (b.specifier) {
1998 .none => .unsigned,
1999 .char => .uchar,
2000 .short => .ushort,
2001 .short_int => .ushort_int,
2002 .int => .uint,
2003 .long => .ulong,
2004 .long_int => .ulong_int,
2005 .long_long => .ulong_long,
2006 .long_long_int => .ulong_long_int,
2007 .int128 => .uint128,
2008 .bit_int => |bits| .{ .ubit_int = bits },
2009 .complex => .complex_unsigned,
2010 .complex_char => .complex_uchar,
2011 .complex_short => .complex_ushort,
2012 .complex_short_int => .complex_ushort_int,
2013 .complex_int => .complex_uint,
2014 .complex_long => .complex_ulong,
2015 .complex_long_int => .complex_ulong_int,
2016 .complex_long_long => .complex_ulong_long,
2017 .complex_long_long_int => .complex_ulong_long_int,
2018 .complex_int128 => .complex_uint128,
2019 .complex_bit_int => |bits| .{ .complex_ubit_int = bits },
2020 .unsigned,
2021 .ushort,
2022 .ushort_int,
2023 .uint,
2024 .ulong,
2025 .ulong_int,
2026 .ulong_long,
2027 .ulong_long_int,
2028 .uint128,
2029 .ubit_int,
2030 .complex_uchar,
2031 .complex_unsigned,
2032 .complex_ushort,
2033 .complex_ushort_int,
2034 .complex_uint,
2035 .complex_ulong,
2036 .complex_ulong_int,
2037 .complex_ulong_long,
2038 .complex_ulong_long_int,
2039 .complex_uint128,
2040 .complex_ubit_int,
2041 => return b.duplicateSpec(p, source_tok, "unsigned"),
2042 else => return b.cannotCombine(p, source_tok),
2043 },
2044 .char => b.specifier = switch (b.specifier) {
2045 .none => .char,
2046 .unsigned => .uchar,
2047 .signed => .schar,
2048 .complex => .complex_char,
2049 .complex_signed => .complex_schar,
2050 .complex_unsigned => .complex_uchar,
2051 else => return b.cannotCombine(p, source_tok),
2052 },
2053 .short => b.specifier = switch (b.specifier) {
2054 .none => .short,
2055 .unsigned => .ushort,
2056 .signed => .sshort,
2057 .int => .short_int,
2058 .sint => .sshort_int,
2059 .uint => .ushort_int,
2060 .complex => .complex_short,
2061 .complex_signed => .complex_sshort,
2062 .complex_unsigned => .complex_ushort,
2063 else => return b.cannotCombine(p, source_tok),
2064 },
2065 .int => b.specifier = switch (b.specifier) {
2066 .none => .int,
2067 .signed => .sint,
2068 .unsigned => .uint,
2069 .short => .short_int,
2070 .sshort => .sshort_int,
2071 .ushort => .ushort_int,
2072 .long => .long_int,
2073 .slong => .slong_int,
2074 .ulong => .ulong_int,
2075 .long_long => .long_long_int,
2076 .slong_long => .slong_long_int,
2077 .ulong_long => .ulong_long_int,
2078 .complex => .complex_int,
2079 .complex_signed => .complex_sint,
2080 .complex_unsigned => .complex_uint,
2081 .complex_short => .complex_short_int,
2082 .complex_sshort => .complex_sshort_int,
2083 .complex_ushort => .complex_ushort_int,
2084 .complex_long => .complex_long_int,
2085 .complex_slong => .complex_slong_int,
2086 .complex_ulong => .complex_ulong_int,
2087 .complex_long_long => .complex_long_long_int,
2088 .complex_slong_long => .complex_slong_long_int,
2089 .complex_ulong_long => .complex_ulong_long_int,
2090 else => return b.cannotCombine(p, source_tok),
2091 },
2092 .long => b.specifier = switch (b.specifier) {
2093 .none => .long,
2094 .double => .long_double,
2095 .long => .long_long,
2096 .unsigned => .ulong,
2097 .signed => .long,
2098 .int => .long_int,
2099 .sint => .slong_int,
2100 .ulong => .ulong_long,
2101 .complex => .complex_long,
2102 .complex_signed => .complex_slong,
2103 .complex_unsigned => .complex_ulong,
2104 .complex_long => .complex_long_long,
2105 .complex_slong => .complex_slong_long,
2106 .complex_ulong => .complex_ulong_long,
2107 .complex_double => .complex_long_double,
2108 else => return b.cannotCombine(p, source_tok),
2109 },
2110 .int128 => b.specifier = switch (b.specifier) {
2111 .none => .int128,
2112 .unsigned => .uint128,
2113 .signed => .sint128,
2114 .complex => .complex_int128,
2115 .complex_signed => .complex_sint128,
2116 .complex_unsigned => .complex_uint128,
2117 else => return b.cannotCombine(p, source_tok),
2118 },
2119 .bit_int => b.specifier = switch (b.specifier) {
2120 .none => .{ .bit_int = new.bit_int },
2121 .unsigned => .{ .ubit_int = new.bit_int },
2122 .signed => .{ .sbit_int = new.bit_int },
2123 .complex => .{ .complex_bit_int = new.bit_int },
2124 .complex_signed => .{ .complex_sbit_int = new.bit_int },
2125 .complex_unsigned => .{ .complex_ubit_int = new.bit_int },
2126 else => return b.cannotCombine(p, source_tok),
2127 },
2128 .auto_type => b.specifier = switch (b.specifier) {
2129 .none => .auto_type,
2130 else => return b.cannotCombine(p, source_tok),
2131 },
2132 .c23_auto => b.specifier = switch (b.specifier) {
2133 .none => .c23_auto,
2134 else => return b.cannotCombine(p, source_tok),
2135 },
2136 .fp16 => b.specifier = switch (b.specifier) {
2137 .none => .fp16,
2138 else => return b.cannotCombine(p, source_tok),
2139 },
2140 .float16 => b.specifier = switch (b.specifier) {
2141 .none => .float16,
2142 .complex => .complex_float16,
2143 else => return b.cannotCombine(p, source_tok),
2144 },
2145 .float => b.specifier = switch (b.specifier) {
2146 .none => .float,
2147 .complex => .complex_float,
2148 else => return b.cannotCombine(p, source_tok),
2149 },
2150 .double => b.specifier = switch (b.specifier) {
2151 .none => .double,
2152 .long => .long_double,
2153 .complex_long => .complex_long_double,
2154 .complex => .complex_double,
2155 else => return b.cannotCombine(p, source_tok),
2156 },
2157 .float128 => b.specifier = switch (b.specifier) {
2158 .none => .float128,
2159 .complex => .complex_float128,
2160 else => return b.cannotCombine(p, source_tok),
2161 },
2162 .complex => b.specifier = switch (b.specifier) {
2163 .none => .complex,
2164 .float16 => .complex_float16,
2165 .float => .complex_float,
2166 .double => .complex_double,
2167 .long_double => .complex_long_double,
2168 .float128 => .complex_float128,
2169 .char => .complex_char,
2170 .schar => .complex_schar,
2171 .uchar => .complex_uchar,
2172 .unsigned => .complex_unsigned,
2173 .signed => .complex_signed,
2174 .short => .complex_short,
2175 .sshort => .complex_sshort,
2176 .ushort => .complex_ushort,
2177 .short_int => .complex_short_int,
2178 .sshort_int => .complex_sshort_int,
2179 .ushort_int => .complex_ushort_int,
2180 .int => .complex_int,
2181 .sint => .complex_sint,
2182 .uint => .complex_uint,
2183 .long => .complex_long,
2184 .slong => .complex_slong,
2185 .ulong => .complex_ulong,
2186 .long_int => .complex_long_int,
2187 .slong_int => .complex_slong_int,
2188 .ulong_int => .complex_ulong_int,
2189 .long_long => .complex_long_long,
2190 .slong_long => .complex_slong_long,
2191 .ulong_long => .complex_ulong_long,
2192 .long_long_int => .complex_long_long_int,
2193 .slong_long_int => .complex_slong_long_int,
2194 .ulong_long_int => .complex_ulong_long_int,
2195 .int128 => .complex_int128,
2196 .sint128 => .complex_sint128,
2197 .uint128 => .complex_uint128,
2198 .bit_int => |bits| .{ .complex_bit_int = bits },
2199 .sbit_int => |bits| .{ .complex_sbit_int = bits },
2200 .ubit_int => |bits| .{ .complex_ubit_int = bits },
2201 .complex,
2202 .complex_float,
2203 .complex_double,
2204 .complex_long_double,
2205 .complex_float128,
2206 .complex_char,
2207 .complex_schar,
2208 .complex_uchar,
2209 .complex_unsigned,
2210 .complex_signed,
2211 .complex_short,
2212 .complex_sshort,
2213 .complex_ushort,
2214 .complex_short_int,
2215 .complex_sshort_int,
2216 .complex_ushort_int,
2217 .complex_int,
2218 .complex_sint,
2219 .complex_uint,
2220 .complex_long,
2221 .complex_slong,
2222 .complex_ulong,
2223 .complex_long_int,
2224 .complex_slong_int,
2225 .complex_ulong_int,
2226 .complex_long_long,
2227 .complex_slong_long,
2228 .complex_ulong_long,
2229 .complex_long_long_int,
2230 .complex_slong_long_int,
2231 .complex_ulong_long_int,
2232 .complex_int128,
2233 .complex_sint128,
2234 .complex_uint128,
2235 .complex_bit_int,
2236 .complex_sbit_int,
2237 .complex_ubit_int,
2238 => return b.duplicateSpec(p, source_tok, "_Complex"),
2239 else => return b.cannotCombine(p, source_tok),
2240 },
2241 }
2242 }
2243
2244 pub fn fromType(ty: Type) Builder.Specifier {
2245 return switch (ty.specifier) {
2246 .void => .void,
2247 .auto_type => .auto_type,
2248 .c23_auto => .c23_auto,
2249 .nullptr_t => .nullptr_t,
2250 .bool => .bool,
2251 .char => .char,
2252 .schar => .schar,
2253 .uchar => .uchar,
2254 .short => .short,
2255 .ushort => .ushort,
2256 .int => .int,
2257 .uint => .uint,
2258 .long => .long,
2259 .ulong => .ulong,
2260 .long_long => .long_long,
2261 .ulong_long => .ulong_long,
2262 .int128 => .int128,
2263 .uint128 => .uint128,
2264 .bit_int => if (ty.data.int.signedness == .unsigned) {
2265 return .{ .ubit_int = ty.data.int.bits };
2266 } else {
2267 return .{ .bit_int = ty.data.int.bits };
2268 },
2269 .complex_char => .complex_char,
2270 .complex_schar => .complex_schar,
2271 .complex_uchar => .complex_uchar,
2272 .complex_short => .complex_short,
2273 .complex_ushort => .complex_ushort,
2274 .complex_int => .complex_int,
2275 .complex_uint => .complex_uint,
2276 .complex_long => .complex_long,
2277 .complex_ulong => .complex_ulong,
2278 .complex_long_long => .complex_long_long,
2279 .complex_ulong_long => .complex_ulong_long,
2280 .complex_int128 => .complex_int128,
2281 .complex_uint128 => .complex_uint128,
2282 .complex_bit_int => if (ty.data.int.signedness == .unsigned) {
2283 return .{ .complex_ubit_int = ty.data.int.bits };
2284 } else {
2285 return .{ .complex_bit_int = ty.data.int.bits };
2286 },
2287 .fp16 => .fp16,
2288 .float16 => .float16,
2289 .float => .float,
2290 .double => .double,
2291 .float128 => .float128,
2292 .long_double => .long_double,
2293 .complex_float16 => .complex_float16,
2294 .complex_float => .complex_float,
2295 .complex_double => .complex_double,
2296 .complex_long_double => .complex_long_double,
2297 .complex_float128 => .complex_float128,
2298
2299 .pointer => .{ .pointer = ty.data.sub_type },
2300 .unspecified_variable_len_array => if (ty.isDecayed())
2301 .{ .decayed_unspecified_variable_len_array = ty.data.sub_type }
2302 else
2303 .{ .unspecified_variable_len_array = ty.data.sub_type },
2304 .func => .{ .func = ty.data.func },
2305 .var_args_func => .{ .var_args_func = ty.data.func },
2306 .old_style_func => .{ .old_style_func = ty.data.func },
2307 .array => if (ty.isDecayed())
2308 .{ .decayed_array = ty.data.array }
2309 else
2310 .{ .array = ty.data.array },
2311 .static_array => if (ty.isDecayed())
2312 .{ .decayed_static_array = ty.data.array }
2313 else
2314 .{ .static_array = ty.data.array },
2315 .incomplete_array => if (ty.isDecayed())
2316 .{ .decayed_incomplete_array = ty.data.array }
2317 else
2318 .{ .incomplete_array = ty.data.array },
2319 .vector => .{ .vector = ty.data.array },
2320 .variable_len_array => if (ty.isDecayed())
2321 .{ .decayed_variable_len_array = ty.data.expr }
2322 else
2323 .{ .variable_len_array = ty.data.expr },
2324 .@"struct" => .{ .@"struct" = ty.data.record },
2325 .@"union" => .{ .@"union" = ty.data.record },
2326 .@"enum" => .{ .@"enum" = ty.data.@"enum" },
2327
2328 .typeof_type => if (ty.isDecayed())
2329 .{ .decayed_typeof_type = ty.data.sub_type }
2330 else
2331 .{ .typeof_type = ty.data.sub_type },
2332 .typeof_expr => if (ty.isDecayed())
2333 .{ .decayed_typeof_expr = ty.data.expr }
2334 else
2335 .{ .typeof_expr = ty.data.expr },
2336
2337 .attributed => if (ty.isDecayed())
2338 .{ .decayed_attributed = ty.data.attributed }
2339 else
2340 .{ .attributed = ty.data.attributed },
2341 else => unreachable,
2342 };
2343 }
2344};
2345
2346/// Use with caution
2347pub fn base(ty: *Type) *Type {
2348 return switch (ty.specifier) {
2349 .typeof_type => ty.data.sub_type.base(),
2350 .typeof_expr => ty.data.expr.ty.base(),
2351 .attributed => ty.data.attributed.base.base(),
2352 else => ty,
2353 };
2354}
2355
2356pub fn getAttribute(ty: Type, comptime tag: Attribute.Tag) ?Attribute.ArgumentsForTag(tag) {
2357 if (tag == .aligned) @compileError("use requestedAlignment");
2358 var it = Attribute.Iterator.initType(ty);
2359 while (it.next()) |item| {
2360 const attribute, _ = item;
2361 if (attribute.tag == tag) return @field(attribute.args, @tagName(tag));
2362 }
2363 return null;
2364}
2365
2366pub fn hasAttribute(ty: Type, tag: Attribute.Tag) bool {
2367 var it = Attribute.Iterator.initType(ty);
2368 while (it.next()) |item| {
2369 const attr, _ = item;
2370 if (attr.tag == tag) return true;
2371 }
2372 return false;
2373}
2374
2375/// printf format modifier
2376pub fn formatModifier(ty: Type) []const u8 {
2377 return switch (ty.specifier) {
2378 .schar, .uchar => "hh",
2379 .short, .ushort => "h",
2380 .int, .uint => "",
2381 .long, .ulong => "l",
2382 .long_long, .ulong_long => "ll",
2383 else => unreachable,
2384 };
2385}
2386
2387/// Suffix for integer values of this type
2388pub fn intValueSuffix(ty: Type, comp: *const Compilation) []const u8 {
2389 return switch (ty.specifier) {
2390 .schar, .short, .int => "",
2391 .long => "L",
2392 .long_long => "LL",
2393 .uchar, .char => {
2394 if (ty.specifier == .char and comp.getCharSignedness() == .signed) return "";
2395 // Only 8-bit char supported currently;
2396 // TODO: handle platforms with 16-bit int + 16-bit char
2397 std.debug.assert(ty.sizeof(comp).? == 1);
2398 return "";
2399 },
2400 .ushort => {
2401 if (ty.sizeof(comp).? < int.sizeof(comp).?) {
2402 return "";
2403 }
2404 return "U";
2405 },
2406 .uint => "U",
2407 .ulong => "UL",
2408 .ulong_long => "ULL",
2409 else => unreachable, // not integer
2410 };
2411}
2412
2413/// Print type in C style
2414pub fn print(ty: Type, mapper: StringInterner.TypeMapper, langopts: LangOpts, w: anytype) @TypeOf(w).Error!void {
2415 _ = try ty.printPrologue(mapper, langopts, w);
2416 try ty.printEpilogue(mapper, langopts, w);
2417}
2418
2419pub fn printNamed(ty: Type, name: []const u8, mapper: StringInterner.TypeMapper, langopts: LangOpts, w: anytype) @TypeOf(w).Error!void {
2420 const simple = try ty.printPrologue(mapper, langopts, w);
2421 if (simple) try w.writeByte(' ');
2422 try w.writeAll(name);
2423 try ty.printEpilogue(mapper, langopts, w);
2424}
2425
2426const StringGetter = fn (TokenIndex) []const u8;
2427
2428/// return true if `ty` is simple
2429fn printPrologue(ty: Type, mapper: StringInterner.TypeMapper, langopts: LangOpts, w: anytype) @TypeOf(w).Error!bool {
2430 if (ty.qual.atomic) {
2431 var non_atomic_ty = ty;
2432 non_atomic_ty.qual.atomic = false;
2433 try w.writeAll("_Atomic(");
2434 try non_atomic_ty.print(mapper, langopts, w);
2435 try w.writeAll(")");
2436 return true;
2437 }
2438 if (ty.isPtr()) {
2439 const elem_ty = ty.elemType();
2440 const simple = try elem_ty.printPrologue(mapper, langopts, w);
2441 if (simple) try w.writeByte(' ');
2442 if (elem_ty.isFunc() or elem_ty.isArray()) try w.writeByte('(');
2443 try w.writeByte('*');
2444 try ty.qual.dump(w);
2445 return false;
2446 }
2447 switch (ty.specifier) {
2448 .pointer => unreachable,
2449 .func, .var_args_func, .old_style_func => {
2450 const ret_ty = ty.data.func.return_type;
2451 const simple = try ret_ty.printPrologue(mapper, langopts, w);
2452 if (simple) try w.writeByte(' ');
2453 return false;
2454 },
2455 .array, .static_array, .incomplete_array, .unspecified_variable_len_array, .variable_len_array => {
2456 const elem_ty = ty.elemType();
2457 const simple = try elem_ty.printPrologue(mapper, langopts, w);
2458 if (simple) try w.writeByte(' ');
2459 return false;
2460 },
2461 .typeof_type, .typeof_expr => {
2462 const actual = ty.canonicalize(.standard);
2463 return actual.printPrologue(mapper, langopts, w);
2464 },
2465 .attributed => {
2466 const actual = ty.canonicalize(.standard);
2467 return actual.printPrologue(mapper, langopts, w);
2468 },
2469 else => {},
2470 }
2471 try ty.qual.dump(w);
2472
2473 switch (ty.specifier) {
2474 .@"enum" => if (ty.data.@"enum".fixed) {
2475 try w.print("enum {s}: ", .{mapper.lookup(ty.data.@"enum".name)});
2476 try ty.data.@"enum".tag_ty.dump(mapper, langopts, w);
2477 } else {
2478 try w.print("enum {s}", .{mapper.lookup(ty.data.@"enum".name)});
2479 },
2480 .@"struct" => try w.print("struct {s}", .{mapper.lookup(ty.data.record.name)}),
2481 .@"union" => try w.print("union {s}", .{mapper.lookup(ty.data.record.name)}),
2482 .vector => {
2483 const len = ty.data.array.len;
2484 const elem_ty = ty.data.array.elem;
2485 try w.print("__attribute__((__vector_size__({d} * sizeof(", .{len});
2486 _ = try elem_ty.printPrologue(mapper, langopts, w);
2487 try w.writeAll(")))) ");
2488 _ = try elem_ty.printPrologue(mapper, langopts, w);
2489 try w.print(" (vector of {d} '", .{len});
2490 _ = try elem_ty.printPrologue(mapper, langopts, w);
2491 try w.writeAll("' values)");
2492 },
2493 .bit_int => try w.print("{s} _BitInt({d})", .{ @tagName(ty.data.int.signedness), ty.data.int.bits }),
2494 .complex_bit_int => try w.print("_Complex {s} _BitInt({d})", .{ @tagName(ty.data.int.signedness), ty.data.int.bits }),
2495 else => try w.writeAll(Builder.fromType(ty).str(langopts).?),
2496 }
2497 return true;
2498}
2499
2500fn printEpilogue(ty: Type, mapper: StringInterner.TypeMapper, langopts: LangOpts, w: anytype) @TypeOf(w).Error!void {
2501 if (ty.qual.atomic) return;
2502 if (ty.isPtr()) {
2503 const elem_ty = ty.elemType();
2504 if (elem_ty.isFunc() or elem_ty.isArray()) try w.writeByte(')');
2505 try elem_ty.printEpilogue(mapper, langopts, w);
2506 return;
2507 }
2508 switch (ty.specifier) {
2509 .pointer => unreachable, // handled above
2510 .func, .var_args_func, .old_style_func => {
2511 try w.writeByte('(');
2512 for (ty.data.func.params, 0..) |param, i| {
2513 if (i != 0) try w.writeAll(", ");
2514 _ = try param.ty.printPrologue(mapper, langopts, w);
2515 try param.ty.printEpilogue(mapper, langopts, w);
2516 }
2517 if (ty.specifier != .func) {
2518 if (ty.data.func.params.len != 0) try w.writeAll(", ");
2519 try w.writeAll("...");
2520 } else if (ty.data.func.params.len == 0) {
2521 try w.writeAll("void");
2522 }
2523 try w.writeByte(')');
2524 try ty.data.func.return_type.printEpilogue(mapper, langopts, w);
2525 },
2526 .array, .static_array => {
2527 try w.writeByte('[');
2528 if (ty.specifier == .static_array) try w.writeAll("static ");
2529 try ty.qual.dump(w);
2530 try w.print("{d}]", .{ty.data.array.len});
2531 try ty.data.array.elem.printEpilogue(mapper, langopts, w);
2532 },
2533 .incomplete_array => {
2534 try w.writeByte('[');
2535 try ty.qual.dump(w);
2536 try w.writeByte(']');
2537 try ty.data.array.elem.printEpilogue(mapper, langopts, w);
2538 },
2539 .unspecified_variable_len_array => {
2540 try w.writeByte('[');
2541 try ty.qual.dump(w);
2542 try w.writeAll("*]");
2543 try ty.data.sub_type.printEpilogue(mapper, langopts, w);
2544 },
2545 .variable_len_array => {
2546 try w.writeByte('[');
2547 try ty.qual.dump(w);
2548 try w.writeAll("<expr>]");
2549 try ty.data.expr.ty.printEpilogue(mapper, langopts, w);
2550 },
2551 .typeof_type, .typeof_expr => {
2552 const actual = ty.canonicalize(.standard);
2553 try actual.printEpilogue(mapper, langopts, w);
2554 },
2555 .attributed => {
2556 const actual = ty.canonicalize(.standard);
2557 try actual.printEpilogue(mapper, langopts, w);
2558 },
2559 else => {},
2560 }
2561}
2562
2563/// Useful for debugging, too noisy to be enabled by default.
2564const dump_detailed_containers = false;
2565
2566// Print as Zig types since those are actually readable
2567pub fn dump(ty: Type, mapper: StringInterner.TypeMapper, langopts: LangOpts, w: anytype) @TypeOf(w).Error!void {
2568 try ty.qual.dump(w);
2569 switch (ty.specifier) {
2570 .invalid => try w.writeAll("invalid"),
2571 .pointer => {
2572 try w.writeAll("*");
2573 try ty.data.sub_type.dump(mapper, langopts, w);
2574 },
2575 .func, .var_args_func, .old_style_func => {
2576 if (ty.specifier == .old_style_func)
2577 try w.writeAll("kr (")
2578 else
2579 try w.writeAll("fn (");
2580 for (ty.data.func.params, 0..) |param, i| {
2581 if (i != 0) try w.writeAll(", ");
2582 if (param.name != .empty) try w.print("{s}: ", .{mapper.lookup(param.name)});
2583 try param.ty.dump(mapper, langopts, w);
2584 }
2585 if (ty.specifier != .func) {
2586 if (ty.data.func.params.len != 0) try w.writeAll(", ");
2587 try w.writeAll("...");
2588 }
2589 try w.writeAll(") ");
2590 try ty.data.func.return_type.dump(mapper, langopts, w);
2591 },
2592 .array, .static_array => {
2593 if (ty.isDecayed()) try w.writeAll("*d");
2594 try w.writeByte('[');
2595 if (ty.specifier == .static_array) try w.writeAll("static ");
2596 try w.print("{d}]", .{ty.data.array.len});
2597 try ty.data.array.elem.dump(mapper, langopts, w);
2598 },
2599 .vector => {
2600 try w.print("vector({d}, ", .{ty.data.array.len});
2601 try ty.data.array.elem.dump(mapper, langopts, w);
2602 try w.writeAll(")");
2603 },
2604 .incomplete_array => {
2605 if (ty.isDecayed()) try w.writeAll("*d");
2606 try w.writeAll("[]");
2607 try ty.data.array.elem.dump(mapper, langopts, w);
2608 },
2609 .@"enum" => {
2610 const enum_ty = ty.data.@"enum";
2611 if (enum_ty.isIncomplete() and !enum_ty.fixed) {
2612 try w.print("enum {s}", .{mapper.lookup(enum_ty.name)});
2613 } else {
2614 try w.print("enum {s}: ", .{mapper.lookup(enum_ty.name)});
2615 try enum_ty.tag_ty.dump(mapper, langopts, w);
2616 }
2617 if (dump_detailed_containers) try dumpEnum(enum_ty, mapper, w);
2618 },
2619 .@"struct" => {
2620 try w.print("struct {s}", .{mapper.lookup(ty.data.record.name)});
2621 if (dump_detailed_containers) try dumpRecord(ty.data.record, mapper, langopts, w);
2622 },
2623 .@"union" => {
2624 try w.print("union {s}", .{mapper.lookup(ty.data.record.name)});
2625 if (dump_detailed_containers) try dumpRecord(ty.data.record, mapper, langopts, w);
2626 },
2627 .unspecified_variable_len_array => {
2628 if (ty.isDecayed()) try w.writeAll("*d");
2629 try w.writeAll("[*]");
2630 try ty.data.sub_type.dump(mapper, langopts, w);
2631 },
2632 .variable_len_array => {
2633 if (ty.isDecayed()) try w.writeAll("*d");
2634 try w.writeAll("[<expr>]");
2635 try ty.data.expr.ty.dump(mapper, langopts, w);
2636 },
2637 .typeof_type => {
2638 try w.writeAll("typeof(");
2639 try ty.data.sub_type.dump(mapper, langopts, w);
2640 try w.writeAll(")");
2641 },
2642 .typeof_expr => {
2643 try w.writeAll("typeof(<expr>: ");
2644 try ty.data.expr.ty.dump(mapper, langopts, w);
2645 try w.writeAll(")");
2646 },
2647 .attributed => {
2648 if (ty.isDecayed()) try w.writeAll("*d:");
2649 try w.writeAll("attributed(");
2650 try ty.data.attributed.base.canonicalize(.standard).dump(mapper, langopts, w);
2651 try w.writeAll(")");
2652 },
2653 .bit_int => try w.print("{s} _BitInt({d})", .{ @tagName(ty.data.int.signedness), ty.data.int.bits }),
2654 .complex_bit_int => try w.print("_Complex {s} _BitInt({d})", .{ @tagName(ty.data.int.signedness), ty.data.int.bits }),
2655 else => try w.writeAll(Builder.fromType(ty).str(langopts).?),
2656 }
2657}
2658
2659fn dumpEnum(@"enum": *Enum, mapper: StringInterner.TypeMapper, w: anytype) @TypeOf(w).Error!void {
2660 try w.writeAll(" {");
2661 for (@"enum".fields) |field| {
2662 try w.print(" {s} = {d},", .{ mapper.lookup(field.name), field.value });
2663 }
2664 try w.writeAll(" }");
2665}
2666
2667fn dumpRecord(record: *Record, mapper: StringInterner.TypeMapper, langopts: LangOpts, w: anytype) @TypeOf(w).Error!void {
2668 try w.writeAll(" {");
2669 for (record.fields) |field| {
2670 try w.writeByte(' ');
2671 try field.ty.dump(mapper, langopts, w);
2672 try w.print(" {s}: {d};", .{ mapper.lookup(field.name), field.bit_width });
2673 }
2674 try w.writeAll(" }");
2675}
lib/compiler/aro/aro/Value.zig deleted-1033
...@@ -1,1033 +0,0 @@
1const std = @import("std");
2const assert = std.debug.assert;
3const BigIntConst = std.math.big.int.Const;
4const BigIntMutable = std.math.big.int.Mutable;
5const backend = @import("../backend.zig");
6const Interner = backend.Interner;
7const BigIntSpace = Interner.Tag.Int.BigIntSpace;
8const Compilation = @import("Compilation.zig");
9const Type = @import("Type.zig");
10const target_util = @import("target.zig");
11const annex_g = @import("annex_g.zig");
12
13const Value = @This();
14
15opt_ref: Interner.OptRef = .none,
16
17pub const zero = Value{ .opt_ref = .zero };
18pub const one = Value{ .opt_ref = .one };
19pub const @"null" = Value{ .opt_ref = .null };
20
21pub fn intern(comp: *Compilation, k: Interner.Key) !Value {
22 const r = try comp.interner.put(comp.gpa, k);
23 return .{ .opt_ref = @enumFromInt(@intFromEnum(r)) };
24}
25
26pub fn int(i: anytype, comp: *Compilation) !Value {
27 const info = @typeInfo(@TypeOf(i));
28 if (info == .comptime_int or info.int.signedness == .unsigned) {
29 return intern(comp, .{ .int = .{ .u64 = i } });
30 } else {
31 return intern(comp, .{ .int = .{ .i64 = i } });
32 }
33}
34
35pub fn ref(v: Value) Interner.Ref {
36 std.debug.assert(v.opt_ref != .none);
37 return @enumFromInt(@intFromEnum(v.opt_ref));
38}
39
40pub fn is(v: Value, tag: std.meta.Tag(Interner.Key), comp: *const Compilation) bool {
41 if (v.opt_ref == .none) return false;
42 return comp.interner.get(v.ref()) == tag;
43}
44
45pub fn isArithmetic(v: Value, comp: *const Compilation) bool {
46 if (v.opt_ref == .none) return false;
47 return switch (comp.interner.get(v.ref())) {
48 .int, .float, .complex => true,
49 else => false,
50 };
51}
52
53/// Number of bits needed to hold `v`.
54/// Asserts that `v` is not negative
55pub fn minUnsignedBits(v: Value, comp: *const Compilation) usize {
56 var space: BigIntSpace = undefined;
57 const big = v.toBigInt(&space, comp);
58 assert(big.positive);
59 return big.bitCountAbs();
60}
61
62test "minUnsignedBits" {
63 const Test = struct {
64 fn checkIntBits(comp: *Compilation, v: u64, expected: usize) !void {
65 const val = try intern(comp, .{ .int = .{ .u64 = v } });
66 try std.testing.expectEqual(expected, val.minUnsignedBits(comp));
67 }
68 };
69
70 var comp = Compilation.init(std.testing.allocator, std.fs.cwd());
71 defer comp.deinit();
72 const target_query = try std.Target.Query.parse(.{ .arch_os_abi = "x86_64-linux-gnu" });
73 comp.target = try std.zig.system.resolveTargetQuery(target_query);
74
75 try Test.checkIntBits(&comp, 0, 0);
76 try Test.checkIntBits(&comp, 1, 1);
77 try Test.checkIntBits(&comp, 2, 2);
78 try Test.checkIntBits(&comp, std.math.maxInt(i8), 7);
79 try Test.checkIntBits(&comp, std.math.maxInt(u8), 8);
80 try Test.checkIntBits(&comp, std.math.maxInt(i16), 15);
81 try Test.checkIntBits(&comp, std.math.maxInt(u16), 16);
82 try Test.checkIntBits(&comp, std.math.maxInt(i32), 31);
83 try Test.checkIntBits(&comp, std.math.maxInt(u32), 32);
84 try Test.checkIntBits(&comp, std.math.maxInt(i64), 63);
85 try Test.checkIntBits(&comp, std.math.maxInt(u64), 64);
86}
87
88/// Minimum number of bits needed to represent `v` in 2's complement notation
89/// Asserts that `v` is negative.
90pub fn minSignedBits(v: Value, comp: *const Compilation) usize {
91 var space: BigIntSpace = undefined;
92 const big = v.toBigInt(&space, comp);
93 assert(!big.positive);
94 return big.bitCountTwosComp();
95}
96
97test "minSignedBits" {
98 const Test = struct {
99 fn checkIntBits(comp: *Compilation, v: i64, expected: usize) !void {
100 const val = try intern(comp, .{ .int = .{ .i64 = v } });
101 try std.testing.expectEqual(expected, val.minSignedBits(comp));
102 }
103 };
104
105 var comp = Compilation.init(std.testing.allocator, std.fs.cwd());
106 defer comp.deinit();
107 const target_query = try std.Target.Query.parse(.{ .arch_os_abi = "x86_64-linux-gnu" });
108 comp.target = try std.zig.system.resolveTargetQuery(target_query);
109
110 try Test.checkIntBits(&comp, -1, 1);
111 try Test.checkIntBits(&comp, -2, 2);
112 try Test.checkIntBits(&comp, -10, 5);
113 try Test.checkIntBits(&comp, -101, 8);
114 try Test.checkIntBits(&comp, std.math.minInt(i8), 8);
115 try Test.checkIntBits(&comp, std.math.minInt(i16), 16);
116 try Test.checkIntBits(&comp, std.math.minInt(i32), 32);
117 try Test.checkIntBits(&comp, std.math.minInt(i64), 64);
118}
119
120pub const FloatToIntChangeKind = enum {
121 /// value did not change
122 none,
123 /// floating point number too small or large for destination integer type
124 out_of_range,
125 /// tried to convert a NaN or Infinity
126 overflow,
127 /// fractional value was converted to zero
128 nonzero_to_zero,
129 /// fractional part truncated
130 value_changed,
131};
132
133/// Converts the stored value from a float to an integer.
134/// `.none` value remains unchanged.
135pub fn floatToInt(v: *Value, dest_ty: Type, comp: *Compilation) !FloatToIntChangeKind {
136 if (v.opt_ref == .none) return .none;
137
138 const float_val = v.toFloat(f128, comp);
139 const was_zero = float_val == 0;
140
141 if (dest_ty.is(.bool)) {
142 const was_one = float_val == 1.0;
143 v.* = fromBool(!was_zero);
144 if (was_zero or was_one) return .none;
145 return .value_changed;
146 } else if (dest_ty.isUnsignedInt(comp) and float_val < 0) {
147 v.* = zero;
148 return .out_of_range;
149 }
150
151 const had_fraction = @rem(float_val, 1) != 0;
152 const is_negative = std.math.signbit(float_val);
153 const floored = @floor(@abs(float_val));
154
155 var rational = try std.math.big.Rational.init(comp.gpa);
156 defer rational.deinit();
157 rational.setFloat(f128, floored) catch |err| switch (err) {
158 error.NonFiniteFloat => {
159 v.* = .{};
160 return .overflow;
161 },
162 error.OutOfMemory => return error.OutOfMemory,
163 };
164
165 // The float is reduced in rational.setFloat, so we assert that denominator is equal to one
166 const big_one = BigIntConst{ .limbs = &.{1}, .positive = true };
167 assert(rational.q.toConst().eqlAbs(big_one));
168
169 if (is_negative) {
170 rational.negate();
171 }
172
173 const signedness = dest_ty.signedness(comp);
174 const bits: usize = @intCast(dest_ty.bitSizeof(comp).?);
175
176 // rational.p.truncate(rational.p.toConst(), signedness: Signedness, bit_count: usize)
177 const fits = rational.p.fitsInTwosComp(signedness, bits);
178 v.* = try intern(comp, .{ .int = .{ .big_int = rational.p.toConst() } });
179 try rational.p.truncate(&rational.p, signedness, bits);
180
181 if (!was_zero and v.isZero(comp)) return .nonzero_to_zero;
182 if (!fits) return .out_of_range;
183 if (had_fraction) return .value_changed;
184 return .none;
185}
186
187/// Converts the stored value from an integer to a float.
188/// `.none` value remains unchanged.
189pub fn intToFloat(v: *Value, dest_ty: Type, comp: *Compilation) !void {
190 if (v.opt_ref == .none) return;
191
192 if (dest_ty.isComplex()) {
193 const bits = dest_ty.bitSizeof(comp).?;
194 const cf: Interner.Key.Complex = switch (bits) {
195 32 => .{ .cf16 = .{ v.toFloat(f16, comp), 0 } },
196 64 => .{ .cf32 = .{ v.toFloat(f32, comp), 0 } },
197 128 => .{ .cf64 = .{ v.toFloat(f64, comp), 0 } },
198 160 => .{ .cf80 = .{ v.toFloat(f80, comp), 0 } },
199 256 => .{ .cf128 = .{ v.toFloat(f128, comp), 0 } },
200 else => unreachable,
201 };
202 v.* = try intern(comp, .{ .complex = cf });
203 return;
204 }
205 const bits = dest_ty.bitSizeof(comp).?;
206 return switch (comp.interner.get(v.ref()).int) {
207 inline .u64, .i64 => |data| {
208 const f: Interner.Key.Float = switch (bits) {
209 16 => .{ .f16 = @floatFromInt(data) },
210 32 => .{ .f32 = @floatFromInt(data) },
211 64 => .{ .f64 = @floatFromInt(data) },
212 80 => .{ .f80 = @floatFromInt(data) },
213 128 => .{ .f128 = @floatFromInt(data) },
214 else => unreachable,
215 };
216 v.* = try intern(comp, .{ .float = f });
217 },
218 .big_int => |data| {
219 const big_f = bigIntToFloat(data.limbs, data.positive);
220 const f: Interner.Key.Float = switch (bits) {
221 16 => .{ .f16 = @floatCast(big_f) },
222 32 => .{ .f32 = @floatCast(big_f) },
223 64 => .{ .f64 = @floatCast(big_f) },
224 80 => .{ .f80 = @floatCast(big_f) },
225 128 => .{ .f128 = @floatCast(big_f) },
226 else => unreachable,
227 };
228 v.* = try intern(comp, .{ .float = f });
229 },
230 };
231}
232
233pub const IntCastChangeKind = enum {
234 /// value did not change
235 none,
236 /// Truncation occurred (e.g., i32 to i16)
237 truncated,
238 /// Sign conversion occurred (e.g., i32 to u32)
239 sign_changed,
240};
241
242/// Truncates or extends bits based on type.
243/// `.none` value remains unchanged.
244pub fn intCast(v: *Value, dest_ty: Type, comp: *Compilation) !IntCastChangeKind {
245 if (v.opt_ref == .none) return .none;
246
247 const dest_bits: usize = @intCast(dest_ty.bitSizeof(comp).?);
248 const dest_signed = dest_ty.signedness(comp) == .signed;
249
250 var space: BigIntSpace = undefined;
251 const big = v.toBigInt(&space, comp);
252 const value_bits = big.bitCountTwosComp();
253
254 // if big is negative, then is signed.
255 const src_signed = !big.positive;
256 const sign_change = src_signed != dest_signed;
257
258 const limbs = try comp.gpa.alloc(
259 std.math.big.Limb,
260 std.math.big.int.calcTwosCompLimbCount(@max(value_bits, dest_bits)),
261 );
262 defer comp.gpa.free(limbs);
263
264 var result_bigint = BigIntMutable{ .limbs = limbs, .positive = undefined, .len = undefined };
265 result_bigint.truncate(big, dest_ty.signedness(comp), dest_bits);
266
267 v.* = try intern(comp, .{ .int = .{ .big_int = result_bigint.toConst() } });
268
269 const truncation_occurred = value_bits > dest_bits;
270 if (truncation_occurred) {
271 return .truncated;
272 } else if (sign_change) {
273 return .sign_changed;
274 } else {
275 return .none;
276 }
277}
278
279/// Converts the stored value to a float of the specified type
280/// `.none` value remains unchanged.
281pub fn floatCast(v: *Value, dest_ty: Type, comp: *Compilation) !void {
282 if (v.opt_ref == .none) return;
283 const bits = dest_ty.bitSizeof(comp).?;
284 if (dest_ty.isComplex()) {
285 const cf: Interner.Key.Complex = switch (bits) {
286 32 => .{ .cf16 = .{ v.toFloat(f16, comp), v.imag(f16, comp) } },
287 64 => .{ .cf32 = .{ v.toFloat(f32, comp), v.imag(f32, comp) } },
288 128 => .{ .cf64 = .{ v.toFloat(f64, comp), v.imag(f64, comp) } },
289 160 => .{ .cf80 = .{ v.toFloat(f80, comp), v.imag(f80, comp) } },
290 256 => .{ .cf128 = .{ v.toFloat(f128, comp), v.imag(f128, comp) } },
291 else => unreachable,
292 };
293 v.* = try intern(comp, .{ .complex = cf });
294 } else {
295 const f: Interner.Key.Float = switch (bits) {
296 16 => .{ .f16 = v.toFloat(f16, comp) },
297 32 => .{ .f32 = v.toFloat(f32, comp) },
298 64 => .{ .f64 = v.toFloat(f64, comp) },
299 80 => .{ .f80 = v.toFloat(f80, comp) },
300 128 => .{ .f128 = v.toFloat(f128, comp) },
301 else => unreachable,
302 };
303 v.* = try intern(comp, .{ .float = f });
304 }
305}
306
307pub fn imag(v: Value, comptime T: type, comp: *const Compilation) T {
308 return switch (comp.interner.get(v.ref())) {
309 .int => 0.0,
310 .float => 0.0,
311 .complex => |repr| switch (repr) {
312 inline else => |components| return @floatCast(components[1]),
313 },
314 else => unreachable,
315 };
316}
317
318pub fn toFloat(v: Value, comptime T: type, comp: *const Compilation) T {
319 return switch (comp.interner.get(v.ref())) {
320 .int => |repr| switch (repr) {
321 inline .u64, .i64 => |data| @floatFromInt(data),
322 .big_int => |data| @floatCast(bigIntToFloat(data.limbs, data.positive)),
323 },
324 .float => |repr| switch (repr) {
325 inline else => |data| @floatCast(data),
326 },
327 .complex => |repr| switch (repr) {
328 inline else => |components| @floatCast(components[0]),
329 },
330 else => unreachable,
331 };
332}
333
334pub fn realPart(v: Value, comp: *Compilation) !Value {
335 if (v.opt_ref == .none) return v;
336 return switch (comp.interner.get(v.ref())) {
337 .int, .float => v,
338 .complex => |repr| Value.intern(comp, switch (repr) {
339 .cf16 => |components| .{ .float = .{ .f16 = components[0] } },
340 .cf32 => |components| .{ .float = .{ .f32 = components[0] } },
341 .cf64 => |components| .{ .float = .{ .f64 = components[0] } },
342 .cf80 => |components| .{ .float = .{ .f80 = components[0] } },
343 .cf128 => |components| .{ .float = .{ .f128 = components[0] } },
344 }),
345 else => unreachable,
346 };
347}
348
349pub fn imaginaryPart(v: Value, comp: *Compilation) !Value {
350 if (v.opt_ref == .none) return v;
351 return switch (comp.interner.get(v.ref())) {
352 .int, .float => Value.zero,
353 .complex => |repr| Value.intern(comp, switch (repr) {
354 .cf16 => |components| .{ .float = .{ .f16 = components[1] } },
355 .cf32 => |components| .{ .float = .{ .f32 = components[1] } },
356 .cf64 => |components| .{ .float = .{ .f64 = components[1] } },
357 .cf80 => |components| .{ .float = .{ .f80 = components[1] } },
358 .cf128 => |components| .{ .float = .{ .f128 = components[1] } },
359 }),
360 else => unreachable,
361 };
362}
363
364fn bigIntToFloat(limbs: []const std.math.big.Limb, positive: bool) f128 {
365 if (limbs.len == 0) return 0;
366
367 const base = std.math.maxInt(std.math.big.Limb) + 1;
368 var result: f128 = 0;
369 var i: usize = limbs.len;
370 while (i != 0) {
371 i -= 1;
372 const limb: f128 = @as(f128, @floatFromInt(limbs[i]));
373 result = @mulAdd(f128, base, result, limb);
374 }
375 if (positive) {
376 return result;
377 } else {
378 return -result;
379 }
380}
381
382pub fn toBigInt(val: Value, space: *BigIntSpace, comp: *const Compilation) BigIntConst {
383 return switch (comp.interner.get(val.ref()).int) {
384 inline .u64, .i64 => |x| BigIntMutable.init(&space.limbs, x).toConst(),
385 .big_int => |b| b,
386 };
387}
388
389pub fn isZero(v: Value, comp: *const Compilation) bool {
390 if (v.opt_ref == .none) return false;
391 switch (v.ref()) {
392 .zero => return true,
393 .one => return false,
394 .null => return target_util.nullRepr(comp.target) == 0,
395 else => {},
396 }
397 const key = comp.interner.get(v.ref());
398 switch (key) {
399 .float => |repr| switch (repr) {
400 inline else => |data| return data == 0,
401 },
402 .int => |repr| switch (repr) {
403 inline .i64, .u64 => |data| return data == 0,
404 .big_int => |data| return data.eqlZero(),
405 },
406 .complex => |repr| switch (repr) {
407 inline else => |data| return data[0] == 0.0 and data[1] == 0.0,
408 },
409 .bytes => return false,
410 else => unreachable,
411 }
412}
413
414const IsInfKind = enum(i32) {
415 negative = -1,
416 finite = 0,
417 positive = 1,
418 unknown = std.math.maxInt(i32),
419};
420
421pub fn isInfSign(v: Value, comp: *const Compilation) IsInfKind {
422 if (v.opt_ref == .none) return .unknown;
423 return switch (comp.interner.get(v.ref())) {
424 .float => |repr| switch (repr) {
425 inline else => |data| if (std.math.isPositiveInf(data)) .positive else if (std.math.isNegativeInf(data)) .negative else .finite,
426 },
427 else => .unknown,
428 };
429}
430pub fn isInf(v: Value, comp: *const Compilation) bool {
431 if (v.opt_ref == .none) return false;
432 return switch (comp.interner.get(v.ref())) {
433 .float => |repr| switch (repr) {
434 inline else => |data| std.math.isInf(data),
435 },
436 .complex => |repr| switch (repr) {
437 inline else => |components| std.math.isInf(components[0]) or std.math.isInf(components[1]),
438 },
439 else => false,
440 };
441}
442
443pub fn isNan(v: Value, comp: *const Compilation) bool {
444 if (v.opt_ref == .none) return false;
445 return switch (comp.interner.get(v.ref())) {
446 .float => |repr| switch (repr) {
447 inline else => |data| std.math.isNan(data),
448 },
449 .complex => |repr| switch (repr) {
450 inline else => |components| std.math.isNan(components[0]) or std.math.isNan(components[1]),
451 },
452 else => false,
453 };
454}
455
456/// Converts value to zero or one;
457/// `.none` value remains unchanged.
458pub fn boolCast(v: *Value, comp: *const Compilation) void {
459 if (v.opt_ref == .none) return;
460 v.* = fromBool(v.toBool(comp));
461}
462
463pub fn fromBool(b: bool) Value {
464 return if (b) one else zero;
465}
466
467pub fn toBool(v: Value, comp: *const Compilation) bool {
468 return !v.isZero(comp);
469}
470
471pub fn toInt(v: Value, comptime T: type, comp: *const Compilation) ?T {
472 if (v.opt_ref == .none) return null;
473 if (comp.interner.get(v.ref()) != .int) return null;
474 var space: BigIntSpace = undefined;
475 const big_int = v.toBigInt(&space, comp);
476 return big_int.to(T) catch null;
477}
478
479const ComplexOp = enum {
480 add,
481 sub,
482};
483
484fn complexAddSub(lhs: Value, rhs: Value, comptime T: type, op: ComplexOp, comp: *Compilation) !Value {
485 const res_re = switch (op) {
486 .add => lhs.toFloat(T, comp) + rhs.toFloat(T, comp),
487 .sub => lhs.toFloat(T, comp) - rhs.toFloat(T, comp),
488 };
489 const res_im = switch (op) {
490 .add => lhs.imag(T, comp) + rhs.imag(T, comp),
491 .sub => lhs.imag(T, comp) - rhs.imag(T, comp),
492 };
493
494 return switch (T) {
495 f16 => intern(comp, .{ .complex = .{ .cf16 = .{ res_re, res_im } } }),
496 f32 => intern(comp, .{ .complex = .{ .cf32 = .{ res_re, res_im } } }),
497 f64 => intern(comp, .{ .complex = .{ .cf64 = .{ res_re, res_im } } }),
498 f80 => intern(comp, .{ .complex = .{ .cf80 = .{ res_re, res_im } } }),
499 f128 => intern(comp, .{ .complex = .{ .cf128 = .{ res_re, res_im } } }),
500 else => unreachable,
501 };
502}
503
504pub fn add(res: *Value, lhs: Value, rhs: Value, ty: Type, comp: *Compilation) !bool {
505 const bits: usize = @intCast(ty.bitSizeof(comp).?);
506 if (ty.isFloat()) {
507 if (ty.isComplex()) {
508 res.* = switch (bits) {
509 32 => try complexAddSub(lhs, rhs, f16, .add, comp),
510 64 => try complexAddSub(lhs, rhs, f32, .add, comp),
511 128 => try complexAddSub(lhs, rhs, f64, .add, comp),
512 160 => try complexAddSub(lhs, rhs, f80, .add, comp),
513 256 => try complexAddSub(lhs, rhs, f128, .add, comp),
514 else => unreachable,
515 };
516 return false;
517 }
518 const f: Interner.Key.Float = switch (bits) {
519 16 => .{ .f16 = lhs.toFloat(f16, comp) + rhs.toFloat(f16, comp) },
520 32 => .{ .f32 = lhs.toFloat(f32, comp) + rhs.toFloat(f32, comp) },
521 64 => .{ .f64 = lhs.toFloat(f64, comp) + rhs.toFloat(f64, comp) },
522 80 => .{ .f80 = lhs.toFloat(f80, comp) + rhs.toFloat(f80, comp) },
523 128 => .{ .f128 = lhs.toFloat(f128, comp) + rhs.toFloat(f128, comp) },
524 else => unreachable,
525 };
526 res.* = try intern(comp, .{ .float = f });
527 return false;
528 } else {
529 var lhs_space: BigIntSpace = undefined;
530 var rhs_space: BigIntSpace = undefined;
531 const lhs_bigint = lhs.toBigInt(&lhs_space, comp);
532 const rhs_bigint = rhs.toBigInt(&rhs_space, comp);
533
534 const limbs = try comp.gpa.alloc(
535 std.math.big.Limb,
536 std.math.big.int.calcTwosCompLimbCount(bits),
537 );
538 defer comp.gpa.free(limbs);
539 var result_bigint = BigIntMutable{ .limbs = limbs, .positive = undefined, .len = undefined };
540
541 const overflowed = result_bigint.addWrap(lhs_bigint, rhs_bigint, ty.signedness(comp), bits);
542 res.* = try intern(comp, .{ .int = .{ .big_int = result_bigint.toConst() } });
543 return overflowed;
544 }
545}
546
547pub fn sub(res: *Value, lhs: Value, rhs: Value, ty: Type, comp: *Compilation) !bool {
548 const bits: usize = @intCast(ty.bitSizeof(comp).?);
549 if (ty.isFloat()) {
550 if (ty.isComplex()) {
551 res.* = switch (bits) {
552 32 => try complexAddSub(lhs, rhs, f16, .sub, comp),
553 64 => try complexAddSub(lhs, rhs, f32, .sub, comp),
554 128 => try complexAddSub(lhs, rhs, f64, .sub, comp),
555 160 => try complexAddSub(lhs, rhs, f80, .sub, comp),
556 256 => try complexAddSub(lhs, rhs, f128, .sub, comp),
557 else => unreachable,
558 };
559 return false;
560 }
561 const f: Interner.Key.Float = switch (bits) {
562 16 => .{ .f16 = lhs.toFloat(f16, comp) - rhs.toFloat(f16, comp) },
563 32 => .{ .f32 = lhs.toFloat(f32, comp) - rhs.toFloat(f32, comp) },
564 64 => .{ .f64 = lhs.toFloat(f64, comp) - rhs.toFloat(f64, comp) },
565 80 => .{ .f80 = lhs.toFloat(f80, comp) - rhs.toFloat(f80, comp) },
566 128 => .{ .f128 = lhs.toFloat(f128, comp) - rhs.toFloat(f128, comp) },
567 else => unreachable,
568 };
569 res.* = try intern(comp, .{ .float = f });
570 return false;
571 } else {
572 var lhs_space: BigIntSpace = undefined;
573 var rhs_space: BigIntSpace = undefined;
574 const lhs_bigint = lhs.toBigInt(&lhs_space, comp);
575 const rhs_bigint = rhs.toBigInt(&rhs_space, comp);
576
577 const limbs = try comp.gpa.alloc(
578 std.math.big.Limb,
579 std.math.big.int.calcTwosCompLimbCount(bits),
580 );
581 defer comp.gpa.free(limbs);
582 var result_bigint = BigIntMutable{ .limbs = limbs, .positive = undefined, .len = undefined };
583
584 const overflowed = result_bigint.subWrap(lhs_bigint, rhs_bigint, ty.signedness(comp), bits);
585 res.* = try intern(comp, .{ .int = .{ .big_int = result_bigint.toConst() } });
586 return overflowed;
587 }
588}
589
590pub fn mul(res: *Value, lhs: Value, rhs: Value, ty: Type, comp: *Compilation) !bool {
591 const bits: usize = @intCast(ty.bitSizeof(comp).?);
592 if (ty.isFloat()) {
593 if (ty.isComplex()) {
594 const cf: Interner.Key.Complex = switch (bits) {
595 32 => .{ .cf16 = annex_g.complexFloatMul(f16, lhs.toFloat(f16, comp), lhs.imag(f16, comp), rhs.toFloat(f16, comp), rhs.imag(f16, comp)) },
596 64 => .{ .cf32 = annex_g.complexFloatMul(f32, lhs.toFloat(f32, comp), lhs.imag(f32, comp), rhs.toFloat(f32, comp), rhs.imag(f32, comp)) },
597 128 => .{ .cf64 = annex_g.complexFloatMul(f64, lhs.toFloat(f64, comp), lhs.imag(f64, comp), rhs.toFloat(f64, comp), rhs.imag(f64, comp)) },
598 160 => .{ .cf80 = annex_g.complexFloatMul(f80, lhs.toFloat(f80, comp), lhs.imag(f80, comp), rhs.toFloat(f80, comp), rhs.imag(f80, comp)) },
599 256 => .{ .cf128 = annex_g.complexFloatMul(f128, lhs.toFloat(f128, comp), lhs.imag(f128, comp), rhs.toFloat(f128, comp), rhs.imag(f128, comp)) },
600 else => unreachable,
601 };
602 res.* = try intern(comp, .{ .complex = cf });
603 return false;
604 }
605 const f: Interner.Key.Float = switch (bits) {
606 16 => .{ .f16 = lhs.toFloat(f16, comp) * rhs.toFloat(f16, comp) },
607 32 => .{ .f32 = lhs.toFloat(f32, comp) * rhs.toFloat(f32, comp) },
608 64 => .{ .f64 = lhs.toFloat(f64, comp) * rhs.toFloat(f64, comp) },
609 80 => .{ .f80 = lhs.toFloat(f80, comp) * rhs.toFloat(f80, comp) },
610 128 => .{ .f128 = lhs.toFloat(f128, comp) * rhs.toFloat(f128, comp) },
611 else => unreachable,
612 };
613 res.* = try intern(comp, .{ .float = f });
614 return false;
615 } else {
616 var lhs_space: BigIntSpace = undefined;
617 var rhs_space: BigIntSpace = undefined;
618 const lhs_bigint = lhs.toBigInt(&lhs_space, comp);
619 const rhs_bigint = rhs.toBigInt(&rhs_space, comp);
620
621 const limbs = try comp.gpa.alloc(
622 std.math.big.Limb,
623 lhs_bigint.limbs.len + rhs_bigint.limbs.len,
624 );
625 defer comp.gpa.free(limbs);
626 var result_bigint = BigIntMutable{ .limbs = limbs, .positive = undefined, .len = undefined };
627
628 const limbs_buffer = try comp.gpa.alloc(
629 std.math.big.Limb,
630 std.math.big.int.calcMulLimbsBufferLen(lhs_bigint.limbs.len, rhs_bigint.limbs.len, 1),
631 );
632 defer comp.gpa.free(limbs_buffer);
633
634 result_bigint.mul(lhs_bigint, rhs_bigint, limbs_buffer, comp.gpa);
635
636 const signedness = ty.signedness(comp);
637 const overflowed = !result_bigint.toConst().fitsInTwosComp(signedness, bits);
638 if (overflowed) {
639 result_bigint.truncate(result_bigint.toConst(), signedness, bits);
640 }
641 res.* = try intern(comp, .{ .int = .{ .big_int = result_bigint.toConst() } });
642 return overflowed;
643 }
644}
645
646/// caller guarantees rhs != 0
647pub fn div(res: *Value, lhs: Value, rhs: Value, ty: Type, comp: *Compilation) !bool {
648 const bits: usize = @intCast(ty.bitSizeof(comp).?);
649 if (ty.isFloat()) {
650 if (ty.isComplex()) {
651 const cf: Interner.Key.Complex = switch (bits) {
652 32 => .{ .cf16 = annex_g.complexFloatDiv(f16, lhs.toFloat(f16, comp), lhs.imag(f16, comp), rhs.toFloat(f16, comp), rhs.imag(f16, comp)) },
653 64 => .{ .cf32 = annex_g.complexFloatDiv(f32, lhs.toFloat(f32, comp), lhs.imag(f32, comp), rhs.toFloat(f32, comp), rhs.imag(f32, comp)) },
654 128 => .{ .cf64 = annex_g.complexFloatDiv(f64, lhs.toFloat(f64, comp), lhs.imag(f64, comp), rhs.toFloat(f64, comp), rhs.imag(f64, comp)) },
655 160 => .{ .cf80 = annex_g.complexFloatDiv(f80, lhs.toFloat(f80, comp), lhs.imag(f80, comp), rhs.toFloat(f80, comp), rhs.imag(f80, comp)) },
656 256 => .{ .cf128 = annex_g.complexFloatDiv(f128, lhs.toFloat(f128, comp), lhs.imag(f128, comp), rhs.toFloat(f128, comp), rhs.imag(f128, comp)) },
657 else => unreachable,
658 };
659 res.* = try intern(comp, .{ .complex = cf });
660 return false;
661 }
662 const f: Interner.Key.Float = switch (bits) {
663 16 => .{ .f16 = lhs.toFloat(f16, comp) / rhs.toFloat(f16, comp) },
664 32 => .{ .f32 = lhs.toFloat(f32, comp) / rhs.toFloat(f32, comp) },
665 64 => .{ .f64 = lhs.toFloat(f64, comp) / rhs.toFloat(f64, comp) },
666 80 => .{ .f80 = lhs.toFloat(f80, comp) / rhs.toFloat(f80, comp) },
667 128 => .{ .f128 = lhs.toFloat(f128, comp) / rhs.toFloat(f128, comp) },
668 else => unreachable,
669 };
670 res.* = try intern(comp, .{ .float = f });
671 return false;
672 } else {
673 var lhs_space: BigIntSpace = undefined;
674 var rhs_space: BigIntSpace = undefined;
675 const lhs_bigint = lhs.toBigInt(&lhs_space, comp);
676 const rhs_bigint = rhs.toBigInt(&rhs_space, comp);
677
678 const limbs_q = try comp.gpa.alloc(
679 std.math.big.Limb,
680 lhs_bigint.limbs.len,
681 );
682 defer comp.gpa.free(limbs_q);
683 var result_q = BigIntMutable{ .limbs = limbs_q, .positive = undefined, .len = undefined };
684
685 const limbs_r = try comp.gpa.alloc(
686 std.math.big.Limb,
687 rhs_bigint.limbs.len,
688 );
689 defer comp.gpa.free(limbs_r);
690 var result_r = BigIntMutable{ .limbs = limbs_r, .positive = undefined, .len = undefined };
691
692 const limbs_buffer = try comp.gpa.alloc(
693 std.math.big.Limb,
694 std.math.big.int.calcDivLimbsBufferLen(lhs_bigint.limbs.len, rhs_bigint.limbs.len),
695 );
696 defer comp.gpa.free(limbs_buffer);
697
698 result_q.divTrunc(&result_r, lhs_bigint, rhs_bigint, limbs_buffer);
699
700 res.* = try intern(comp, .{ .int = .{ .big_int = result_q.toConst() } });
701 return !result_q.toConst().fitsInTwosComp(ty.signedness(comp), bits);
702 }
703}
704
705/// caller guarantees rhs != 0
706/// caller guarantees lhs != std.math.minInt(T) OR rhs != -1
707pub fn rem(lhs: Value, rhs: Value, ty: Type, comp: *Compilation) !Value {
708 var lhs_space: BigIntSpace = undefined;
709 var rhs_space: BigIntSpace = undefined;
710 const lhs_bigint = lhs.toBigInt(&lhs_space, comp);
711 const rhs_bigint = rhs.toBigInt(&rhs_space, comp);
712
713 const signedness = ty.signedness(comp);
714 if (signedness == .signed) {
715 var spaces: [2]BigIntSpace = undefined;
716 const min_val = try Value.minInt(ty, comp);
717 const negative = BigIntMutable.init(&spaces[0].limbs, -1).toConst();
718 const big_one = BigIntMutable.init(&spaces[1].limbs, 1).toConst();
719 if (lhs.compare(.eq, min_val, comp) and rhs_bigint.eql(negative)) {
720 return .{};
721 } else if (rhs_bigint.order(big_one).compare(.lt)) {
722 // lhs - @divTrunc(lhs, rhs) * rhs
723 var tmp: Value = undefined;
724 _ = try tmp.div(lhs, rhs, ty, comp);
725 _ = try tmp.mul(tmp, rhs, ty, comp);
726 _ = try tmp.sub(lhs, tmp, ty, comp);
727 return tmp;
728 }
729 }
730
731 const limbs_q = try comp.gpa.alloc(
732 std.math.big.Limb,
733 lhs_bigint.limbs.len,
734 );
735 defer comp.gpa.free(limbs_q);
736 var result_q = BigIntMutable{ .limbs = limbs_q, .positive = undefined, .len = undefined };
737
738 const limbs_r = try comp.gpa.alloc(
739 std.math.big.Limb,
740 rhs_bigint.limbs.len,
741 );
742 defer comp.gpa.free(limbs_r);
743 var result_r = BigIntMutable{ .limbs = limbs_r, .positive = undefined, .len = undefined };
744
745 const limbs_buffer = try comp.gpa.alloc(
746 std.math.big.Limb,
747 std.math.big.int.calcDivLimbsBufferLen(lhs_bigint.limbs.len, rhs_bigint.limbs.len),
748 );
749 defer comp.gpa.free(limbs_buffer);
750
751 result_q.divTrunc(&result_r, lhs_bigint, rhs_bigint, limbs_buffer);
752 return intern(comp, .{ .int = .{ .big_int = result_r.toConst() } });
753}
754
755pub fn bitOr(lhs: Value, rhs: Value, comp: *Compilation) !Value {
756 var lhs_space: BigIntSpace = undefined;
757 var rhs_space: BigIntSpace = undefined;
758 const lhs_bigint = lhs.toBigInt(&lhs_space, comp);
759 const rhs_bigint = rhs.toBigInt(&rhs_space, comp);
760
761 const limbs = try comp.gpa.alloc(
762 std.math.big.Limb,
763 @max(lhs_bigint.limbs.len, rhs_bigint.limbs.len),
764 );
765 defer comp.gpa.free(limbs);
766 var result_bigint = BigIntMutable{ .limbs = limbs, .positive = undefined, .len = undefined };
767
768 result_bigint.bitOr(lhs_bigint, rhs_bigint);
769 return intern(comp, .{ .int = .{ .big_int = result_bigint.toConst() } });
770}
771
772pub fn bitXor(lhs: Value, rhs: Value, comp: *Compilation) !Value {
773 var lhs_space: BigIntSpace = undefined;
774 var rhs_space: BigIntSpace = undefined;
775 const lhs_bigint = lhs.toBigInt(&lhs_space, comp);
776 const rhs_bigint = rhs.toBigInt(&rhs_space, comp);
777
778 const extra = @intFromBool(lhs_bigint.positive != rhs_bigint.positive);
779 const limbs = try comp.gpa.alloc(
780 std.math.big.Limb,
781 @max(lhs_bigint.limbs.len, rhs_bigint.limbs.len) + extra,
782 );
783 defer comp.gpa.free(limbs);
784 var result_bigint = BigIntMutable{ .limbs = limbs, .positive = undefined, .len = undefined };
785
786 result_bigint.bitXor(lhs_bigint, rhs_bigint);
787 return intern(comp, .{ .int = .{ .big_int = result_bigint.toConst() } });
788}
789
790pub fn bitAnd(lhs: Value, rhs: Value, comp: *Compilation) !Value {
791 var lhs_space: BigIntSpace = undefined;
792 var rhs_space: BigIntSpace = undefined;
793 const lhs_bigint = lhs.toBigInt(&lhs_space, comp);
794 const rhs_bigint = rhs.toBigInt(&rhs_space, comp);
795
796 const limb_count = if (lhs_bigint.positive and rhs_bigint.positive)
797 @min(lhs_bigint.limbs.len, rhs_bigint.limbs.len)
798 else if (lhs_bigint.positive)
799 lhs_bigint.limbs.len
800 else if (rhs_bigint.positive)
801 rhs_bigint.limbs.len
802 else
803 @max(lhs_bigint.limbs.len, rhs_bigint.limbs.len) + 1;
804
805 const limbs = try comp.gpa.alloc(std.math.big.Limb, limb_count);
806 defer comp.gpa.free(limbs);
807 var result_bigint = BigIntMutable{ .limbs = limbs, .positive = undefined, .len = undefined };
808
809 result_bigint.bitAnd(lhs_bigint, rhs_bigint);
810 return intern(comp, .{ .int = .{ .big_int = result_bigint.toConst() } });
811}
812
813pub fn bitNot(val: Value, ty: Type, comp: *Compilation) !Value {
814 const bits: usize = @intCast(ty.bitSizeof(comp).?);
815 var val_space: Value.BigIntSpace = undefined;
816 const val_bigint = val.toBigInt(&val_space, comp);
817
818 const limbs = try comp.gpa.alloc(
819 std.math.big.Limb,
820 std.math.big.int.calcTwosCompLimbCount(bits),
821 );
822 defer comp.gpa.free(limbs);
823 var result_bigint = BigIntMutable{ .limbs = limbs, .positive = undefined, .len = undefined };
824
825 result_bigint.bitNotWrap(val_bigint, ty.signedness(comp), bits);
826 return intern(comp, .{ .int = .{ .big_int = result_bigint.toConst() } });
827}
828
829pub fn shl(res: *Value, lhs: Value, rhs: Value, ty: Type, comp: *Compilation) !bool {
830 var lhs_space: Value.BigIntSpace = undefined;
831 const lhs_bigint = lhs.toBigInt(&lhs_space, comp);
832 const shift = rhs.toInt(usize, comp) orelse std.math.maxInt(usize);
833
834 const bits: usize = @intCast(ty.bitSizeof(comp).?);
835 if (shift > bits) {
836 if (lhs_bigint.positive) {
837 res.* = try Value.maxInt(ty, comp);
838 } else {
839 res.* = try Value.minInt(ty, comp);
840 }
841 return true;
842 }
843
844 const limbs = try comp.gpa.alloc(
845 std.math.big.Limb,
846 lhs_bigint.limbs.len + (shift / (@sizeOf(std.math.big.Limb) * 8)) + 1,
847 );
848 defer comp.gpa.free(limbs);
849 var result_bigint = BigIntMutable{ .limbs = limbs, .positive = undefined, .len = undefined };
850
851 result_bigint.shiftLeft(lhs_bigint, shift);
852 const signedness = ty.signedness(comp);
853 const overflowed = !result_bigint.toConst().fitsInTwosComp(signedness, bits);
854 if (overflowed) {
855 result_bigint.truncate(result_bigint.toConst(), signedness, bits);
856 }
857 res.* = try intern(comp, .{ .int = .{ .big_int = result_bigint.toConst() } });
858 return overflowed;
859}
860
861pub fn shr(lhs: Value, rhs: Value, ty: Type, comp: *Compilation) !Value {
862 var lhs_space: Value.BigIntSpace = undefined;
863 const lhs_bigint = lhs.toBigInt(&lhs_space, comp);
864 const shift = rhs.toInt(usize, comp) orelse return zero;
865
866 const result_limbs = lhs_bigint.limbs.len -| (shift / (@sizeOf(std.math.big.Limb) * 8));
867 if (result_limbs == 0) {
868 // The shift is enough to remove all the bits from the number, which means the
869 // result is 0 or -1 depending on the sign.
870 if (lhs_bigint.positive) {
871 return zero;
872 } else {
873 return intern(comp, .{ .int = .{ .i64 = -1 } });
874 }
875 }
876
877 const bits: usize = @intCast(ty.bitSizeof(comp).?);
878 const limbs = try comp.gpa.alloc(
879 std.math.big.Limb,
880 std.math.big.int.calcTwosCompLimbCount(bits),
881 );
882 defer comp.gpa.free(limbs);
883 var result_bigint = BigIntMutable{ .limbs = limbs, .positive = undefined, .len = undefined };
884
885 result_bigint.shiftRight(lhs_bigint, shift);
886 return intern(comp, .{ .int = .{ .big_int = result_bigint.toConst() } });
887}
888
889pub fn complexConj(val: Value, ty: Type, comp: *Compilation) !Value {
890 const bits = ty.bitSizeof(comp).?;
891 const cf: Interner.Key.Complex = switch (bits) {
892 32 => .{ .cf16 = .{ val.toFloat(f16, comp), -val.imag(f16, comp) } },
893 64 => .{ .cf32 = .{ val.toFloat(f32, comp), -val.imag(f32, comp) } },
894 128 => .{ .cf64 = .{ val.toFloat(f64, comp), -val.imag(f64, comp) } },
895 160 => .{ .cf80 = .{ val.toFloat(f80, comp), -val.imag(f80, comp) } },
896 256 => .{ .cf128 = .{ val.toFloat(f128, comp), -val.imag(f128, comp) } },
897 else => unreachable,
898 };
899 return intern(comp, .{ .complex = cf });
900}
901
902pub fn compare(lhs: Value, op: std.math.CompareOperator, rhs: Value, comp: *const Compilation) bool {
903 if (op == .eq) {
904 return lhs.opt_ref == rhs.opt_ref;
905 } else if (lhs.opt_ref == rhs.opt_ref) {
906 return std.math.Order.eq.compare(op);
907 }
908
909 const lhs_key = comp.interner.get(lhs.ref());
910 const rhs_key = comp.interner.get(rhs.ref());
911 if (lhs_key == .float or rhs_key == .float) {
912 const lhs_f128 = lhs.toFloat(f128, comp);
913 const rhs_f128 = rhs.toFloat(f128, comp);
914 return std.math.compare(lhs_f128, op, rhs_f128);
915 }
916 if (lhs_key == .complex or rhs_key == .complex) {
917 assert(op == .neq);
918 const real_equal = std.math.compare(lhs.toFloat(f128, comp), .eq, rhs.toFloat(f128, comp));
919 const imag_equal = std.math.compare(lhs.imag(f128, comp), .eq, rhs.imag(f128, comp));
920 return !real_equal or !imag_equal;
921 }
922
923 var lhs_bigint_space: BigIntSpace = undefined;
924 var rhs_bigint_space: BigIntSpace = undefined;
925 const lhs_bigint = lhs.toBigInt(&lhs_bigint_space, comp);
926 const rhs_bigint = rhs.toBigInt(&rhs_bigint_space, comp);
927 return lhs_bigint.order(rhs_bigint).compare(op);
928}
929
930fn twosCompIntLimit(limit: std.math.big.int.TwosCompIntLimit, ty: Type, comp: *Compilation) !Value {
931 const signedness = ty.signedness(comp);
932 if (limit == .min and signedness == .unsigned) return Value.zero;
933 const mag_bits: usize = @intCast(ty.bitSizeof(comp).?);
934 switch (mag_bits) {
935 inline 8, 16, 32, 64 => |bits| {
936 if (limit == .min) return Value.int(@as(i64, std.math.minInt(std.meta.Int(.signed, bits))), comp);
937 return switch (signedness) {
938 inline else => |sign| Value.int(std.math.maxInt(std.meta.Int(sign, bits)), comp),
939 };
940 },
941 else => {},
942 }
943
944 const sign_bits = @intFromBool(signedness == .signed);
945 const total_bits = mag_bits + sign_bits;
946
947 const limbs = try comp.gpa.alloc(
948 std.math.big.Limb,
949 std.math.big.int.calcTwosCompLimbCount(total_bits),
950 );
951 defer comp.gpa.free(limbs);
952
953 var result_bigint: BigIntMutable = .{ .limbs = limbs, .positive = undefined, .len = undefined };
954 result_bigint.setTwosCompIntLimit(limit, signedness, mag_bits);
955 return Value.intern(comp, .{ .int = .{ .big_int = result_bigint.toConst() } });
956}
957
958pub fn minInt(ty: Type, comp: *Compilation) !Value {
959 return twosCompIntLimit(.min, ty, comp);
960}
961
962pub fn maxInt(ty: Type, comp: *Compilation) !Value {
963 return twosCompIntLimit(.max, ty, comp);
964}
965
966pub fn print(v: Value, ty: Type, comp: *const Compilation, w: anytype) @TypeOf(w).Error!void {
967 if (ty.is(.bool)) {
968 return w.writeAll(if (v.isZero(comp)) "false" else "true");
969 }
970 const key = comp.interner.get(v.ref());
971 switch (key) {
972 .null => return w.writeAll("nullptr_t"),
973 .int => |repr| switch (repr) {
974 inline else => |x| return w.print("{d}", .{x}),
975 },
976 .float => |repr| switch (repr) {
977 .f16 => |x| return w.print("{d}", .{@round(@as(f64, @floatCast(x)) * 1000) / 1000}),
978 .f32 => |x| return w.print("{d}", .{@round(@as(f64, @floatCast(x)) * 1000000) / 1000000}),
979 inline else => |x| return w.print("{d}", .{@as(f64, @floatCast(x))}),
980 },
981 .bytes => |b| return printString(b, ty, comp, w),
982 .complex => |repr| switch (repr) {
983 .cf32 => |components| return w.print("{d} + {d}i", .{ @round(@as(f64, @floatCast(components[0])) * 1000000) / 1000000, @round(@as(f64, @floatCast(components[1])) * 1000000) / 1000000 }),
984 inline else => |components| return w.print("{d} + {d}i", .{ @as(f64, @floatCast(components[0])), @as(f64, @floatCast(components[1])) }),
985 },
986 else => unreachable, // not a value
987 }
988}
989
990pub fn printString(bytes: []const u8, ty: Type, comp: *const Compilation, w: anytype) @TypeOf(w).Error!void {
991 const size: Compilation.CharUnitSize = @enumFromInt(ty.elemType().sizeof(comp).?);
992 const without_null = bytes[0 .. bytes.len - @intFromEnum(size)];
993 try w.writeByte('"');
994 switch (size) {
995 .@"1" => try w.print("{}", .{std.zig.fmtEscapes(without_null)}),
996 .@"2" => {
997 var items: [2]u16 = undefined;
998 var i: usize = 0;
999 while (i < without_null.len) {
1000 @memcpy(std.mem.sliceAsBytes(items[0..1]), without_null[i..][0..2]);
1001 i += 2;
1002 const is_surrogate = std.unicode.utf16IsHighSurrogate(items[0]);
1003 if (is_surrogate and i < without_null.len) {
1004 @memcpy(std.mem.sliceAsBytes(items[1..2]), without_null[i..][0..2]);
1005 if (std.unicode.utf16DecodeSurrogatePair(&items)) |decoded| {
1006 i += 2;
1007 try w.print("{u}", .{decoded});
1008 } else |_| {
1009 try w.print("\\x{x}", .{items[0]});
1010 }
1011 } else if (is_surrogate) {
1012 try w.print("\\x{x}", .{items[0]});
1013 } else {
1014 try w.print("{u}", .{items[0]});
1015 }
1016 }
1017 },
1018 .@"4" => {
1019 var item: [1]u32 = undefined;
1020 const data_slice = std.mem.sliceAsBytes(item[0..1]);
1021 for (0..@divExact(without_null.len, 4)) |n| {
1022 @memcpy(data_slice, without_null[n * 4 ..][0..4]);
1023 if (item[0] <= std.math.maxInt(u21) and std.unicode.utf8ValidCodepoint(@intCast(item[0]))) {
1024 const codepoint: u21 = @intCast(item[0]);
1025 try w.print("{u}", .{codepoint});
1026 } else {
1027 try w.print("\\x{x}", .{item[0]});
1028 }
1029 }
1030 },
1031 }
1032 try w.writeByte('"');
1033}
lib/compiler/aro/aro/annex_g.zig deleted-118
...@@ -1,118 +0,0 @@
1//! Complex arithmetic algorithms from C99 Annex G
2
3const std = @import("std");
4const copysign = std.math.copysign;
5const ilogb = std.math.ilogb;
6const inf = std.math.inf;
7const isFinite = std.math.isFinite;
8const isInf = std.math.isInf;
9const isNan = std.math.isNan;
10const isPositiveZero = std.math.isPositiveZero;
11const scalbn = std.math.scalbn;
12
13/// computes floating point z*w where a_param, b_param are real, imaginary parts of z and c_param, d_param are real, imaginary parts of w
14pub fn complexFloatMul(comptime T: type, a_param: T, b_param: T, c_param: T, d_param: T) [2]T {
15 var a = a_param;
16 var b = b_param;
17 var c = c_param;
18 var d = d_param;
19
20 const ac = a * c;
21 const bd = b * d;
22 const ad = a * d;
23 const bc = b * c;
24 var x = ac - bd;
25 var y = ad + bc;
26 if (isNan(x) and isNan(y)) {
27 var recalc = false;
28 if (isInf(a) or isInf(b)) {
29 // lhs infinite
30 // Box the infinity and change NaNs in the other factor to 0
31 a = copysign(if (isInf(a)) @as(T, 1.0) else @as(T, 0.0), a);
32 b = copysign(if (isInf(b)) @as(T, 1.0) else @as(T, 0.0), b);
33 if (isNan(c)) c = copysign(@as(T, 0.0), c);
34 if (isNan(d)) d = copysign(@as(T, 0.0), d);
35 recalc = true;
36 }
37 if (isInf(c) or isInf(d)) {
38 // rhs infinite
39 // Box the infinity and change NaNs in the other factor to 0
40 c = copysign(if (isInf(c)) @as(T, 1.0) else @as(T, 0.0), c);
41 d = copysign(if (isInf(d)) @as(T, 1.0) else @as(T, 0.0), d);
42 if (isNan(a)) a = copysign(@as(T, 0.0), a);
43 if (isNan(b)) b = copysign(@as(T, 0.0), b);
44 recalc = true;
45 }
46 if (!recalc and (isInf(ac) or isInf(bd) or isInf(ad) or isInf(bc))) {
47 // Recover infinities from overflow by changing NaN's to 0
48 if (isNan(a)) a = copysign(@as(T, 0.0), a);
49 if (isNan(b)) b = copysign(@as(T, 0.0), b);
50 if (isNan(c)) c = copysign(@as(T, 0.0), c);
51 if (isNan(d)) d = copysign(@as(T, 0.0), d);
52 }
53 if (recalc) {
54 x = inf(T) * (a * c - b * d);
55 y = inf(T) * (a * d + b * c);
56 }
57 }
58 return .{ x, y };
59}
60
61/// computes floating point z / w where a_param, b_param are real, imaginary parts of z and c_param, d_param are real, imaginary parts of w
62pub fn complexFloatDiv(comptime T: type, a_param: T, b_param: T, c_param: T, d_param: T) [2]T {
63 var a = a_param;
64 var b = b_param;
65 var c = c_param;
66 var d = d_param;
67 var denom_logb: i32 = 0;
68 const max_cd = @max(@abs(c), @abs(d));
69 if (isFinite(max_cd)) {
70 if (max_cd == 0) {
71 denom_logb = std.math.minInt(i32) + 1;
72 c = 0;
73 d = 0;
74 } else {
75 denom_logb = ilogb(max_cd);
76 c = scalbn(c, -denom_logb);
77 d = scalbn(d, -denom_logb);
78 }
79 }
80 const denom = c * c + d * d;
81 var x = scalbn((a * c + b * d) / denom, -denom_logb);
82 var y = scalbn((b * c - a * d) / denom, -denom_logb);
83 if (isNan(x) and isNan(y)) {
84 if (isPositiveZero(denom) and (!isNan(a) or !isNan(b))) {
85 x = copysign(inf(T), c) * a;
86 y = copysign(inf(T), c) * b;
87 } else if ((isInf(a) or isInf(b)) and isFinite(c) and isFinite(d)) {
88 a = copysign(if (isInf(a)) @as(T, 1.0) else @as(T, 0.0), a);
89 b = copysign(if (isInf(b)) @as(T, 1.0) else @as(T, 0.0), b);
90 x = inf(T) * (a * c + b * d);
91 y = inf(T) * (b * c - a * d);
92 } else if (isInf(max_cd) and isFinite(a) and isFinite(b)) {
93 c = copysign(if (isInf(c)) @as(T, 1.0) else @as(T, 0.0), c);
94 d = copysign(if (isInf(d)) @as(T, 1.0) else @as(T, 0.0), d);
95 x = 0.0 * (a * c + b * d);
96 y = 0.0 * (b * c - a * d);
97 }
98 }
99 return .{ x, y };
100}
101
102test complexFloatMul {
103 // Naive algorithm would produce NaN + NaNi instead of inf + NaNi
104 const result = complexFloatMul(f64, inf(f64), std.math.nan(f64), 2, 0);
105 try std.testing.expect(isInf(result[0]));
106 try std.testing.expect(isNan(result[1]));
107}
108
109test complexFloatDiv {
110 // Naive algorithm would produce NaN + NaNi instead of inf + NaNi
111 var result = complexFloatDiv(f64, inf(f64), std.math.nan(f64), 2, 0);
112 try std.testing.expect(isInf(result[0]));
113 try std.testing.expect(isNan(result[1]));
114
115 result = complexFloatDiv(f64, 2.0, 2.0, 0.0, 0.0);
116 try std.testing.expect(isInf(result[0]));
117 try std.testing.expect(isInf(result[1]));
118}
lib/compiler/aro/aro/char_info.zig deleted-1111
...@@ -1,1111 +0,0 @@
1//! This module provides functions for classifying characters according to
2//! various C standards. All classification routines *do not* consider
3//! characters from the basic character set; it is assumed those will be
4//! checked separately
5//! isXidStart and isXidContinue are adapted from https://github.com/dtolnay/unicode-ident
6
7const assert = @import("std").debug.assert;
8const tables = @import("char_info/identifier_tables.zig");
9
10/// C11 Standard Annex D
11pub fn isC11IdChar(codepoint: u21) bool {
12 assert(codepoint > 0x7F);
13 return switch (codepoint) {
14 // 1
15 0x00A8,
16 0x00AA,
17 0x00AD,
18 0x00AF,
19 0x00B2...0x00B5,
20 0x00B7...0x00BA,
21 0x00BC...0x00BE,
22 0x00C0...0x00D6,
23 0x00D8...0x00F6,
24 0x00F8...0x00FF,
25
26 // 2
27 0x0100...0x167F,
28 0x1681...0x180D,
29 0x180F...0x1FFF,
30
31 // 3
32 0x200B...0x200D,
33 0x202A...0x202E,
34 0x203F...0x2040,
35 0x2054,
36 0x2060...0x206F,
37
38 // 4
39 0x2070...0x218F,
40 0x2460...0x24FF,
41 0x2776...0x2793,
42 0x2C00...0x2DFF,
43 0x2E80...0x2FFF,
44
45 // 5
46 0x3004...0x3007,
47 0x3021...0x302F,
48 0x3031...0x303F,
49
50 // 6
51 0x3040...0xD7FF,
52
53 // 7
54 0xF900...0xFD3D,
55 0xFD40...0xFDCF,
56 0xFDF0...0xFE44,
57 0xFE47...0xFFFD,
58
59 // 8
60 0x10000...0x1FFFD,
61 0x20000...0x2FFFD,
62 0x30000...0x3FFFD,
63 0x40000...0x4FFFD,
64 0x50000...0x5FFFD,
65 0x60000...0x6FFFD,
66 0x70000...0x7FFFD,
67 0x80000...0x8FFFD,
68 0x90000...0x9FFFD,
69 0xA0000...0xAFFFD,
70 0xB0000...0xBFFFD,
71 0xC0000...0xCFFFD,
72 0xD0000...0xDFFFD,
73 0xE0000...0xEFFFD,
74 => true,
75 else => false,
76 };
77}
78
79/// C99 Standard Annex D
80pub fn isC99IdChar(codepoint: u21) bool {
81 assert(codepoint > 0x7F);
82 return switch (codepoint) {
83 // Latin
84 0x00AA,
85 0x00BA,
86 0x00C0...0x00D6,
87 0x00D8...0x00F6,
88 0x00F8...0x01F5,
89 0x01FA...0x0217,
90 0x0250...0x02A8,
91 0x1E00...0x1E9B,
92 0x1EA0...0x1EF9,
93 0x207F,
94
95 // Greek
96 0x0386,
97 0x0388...0x038A,
98 0x038C,
99 0x038E...0x03A1,
100 0x03A3...0x03CE,
101 0x03D0...0x03D6,
102 0x03DA,
103 0x03DC,
104 0x03DE,
105 0x03E0,
106 0x03E2...0x03F3,
107 0x1F00...0x1F15,
108 0x1F18...0x1F1D,
109 0x1F20...0x1F45,
110 0x1F48...0x1F4D,
111 0x1F50...0x1F57,
112 0x1F59,
113 0x1F5B,
114 0x1F5D,
115 0x1F5F...0x1F7D,
116 0x1F80...0x1FB4,
117 0x1FB6...0x1FBC,
118 0x1FC2...0x1FC4,
119 0x1FC6...0x1FCC,
120 0x1FD0...0x1FD3,
121 0x1FD6...0x1FDB,
122 0x1FE0...0x1FEC,
123 0x1FF2...0x1FF4,
124 0x1FF6...0x1FFC,
125
126 // Cyrillic
127 0x0401...0x040C,
128 0x040E...0x044F,
129 0x0451...0x045C,
130 0x045E...0x0481,
131 0x0490...0x04C4,
132 0x04C7...0x04C8,
133 0x04CB...0x04CC,
134 0x04D0...0x04EB,
135 0x04EE...0x04F5,
136 0x04F8...0x04F9,
137
138 // Armenian
139 0x0531...0x0556,
140 0x0561...0x0587,
141
142 // Hebrew
143 0x05B0...0x05B9,
144 0x05BB...0x05BD,
145 0x05BF,
146 0x05C1...0x05C2,
147 0x05D0...0x05EA,
148 0x05F0...0x05F2,
149
150 // Arabic
151 0x0621...0x063A,
152 0x0640...0x0652,
153 0x0670...0x06B7,
154 0x06BA...0x06BE,
155 0x06C0...0x06CE,
156 0x06D0...0x06DC,
157 0x06E5...0x06E8,
158 0x06EA...0x06ED,
159
160 // Devanagari
161 0x0901...0x0903,
162 0x0905...0x0939,
163 0x093E...0x094D,
164 0x0950...0x0952,
165 0x0958...0x0963,
166
167 // Bengali
168 0x0981...0x0983,
169 0x0985...0x098C,
170 0x098F...0x0990,
171 0x0993...0x09A8,
172 0x09AA...0x09B0,
173 0x09B2,
174 0x09B6...0x09B9,
175 0x09BE...0x09C4,
176 0x09C7...0x09C8,
177 0x09CB...0x09CD,
178 0x09DC...0x09DD,
179 0x09DF...0x09E3,
180 0x09F0...0x09F1,
181
182 // Gurmukhi
183 0x0A02,
184 0x0A05...0x0A0A,
185 0x0A0F...0x0A10,
186 0x0A13...0x0A28,
187 0x0A2A...0x0A30,
188 0x0A32...0x0A33,
189 0x0A35...0x0A36,
190 0x0A38...0x0A39,
191 0x0A3E...0x0A42,
192 0x0A47...0x0A48,
193 0x0A4B...0x0A4D,
194 0x0A59...0x0A5C,
195 0x0A5E,
196 0x0A74,
197
198 // Gujarati
199 0x0A81...0x0A83,
200 0x0A85...0x0A8B,
201 0x0A8D,
202 0x0A8F...0x0A91,
203 0x0A93...0x0AA8,
204 0x0AAA...0x0AB0,
205 0x0AB2...0x0AB3,
206 0x0AB5...0x0AB9,
207 0x0ABD...0x0AC5,
208 0x0AC7...0x0AC9,
209 0x0ACB...0x0ACD,
210 0x0AD0,
211 0x0AE0,
212
213 // Oriya
214 0x0B01...0x0B03,
215 0x0B05...0x0B0C,
216 0x0B0F...0x0B10,
217 0x0B13...0x0B28,
218 0x0B2A...0x0B30,
219 0x0B32...0x0B33,
220 0x0B36...0x0B39,
221 0x0B3E...0x0B43,
222 0x0B47...0x0B48,
223 0x0B4B...0x0B4D,
224 0x0B5C...0x0B5D,
225 0x0B5F...0x0B61,
226
227 // Tamil
228 0x0B82...0x0B83,
229 0x0B85...0x0B8A,
230 0x0B8E...0x0B90,
231 0x0B92...0x0B95,
232 0x0B99...0x0B9A,
233 0x0B9C,
234 0x0B9E...0x0B9F,
235 0x0BA3...0x0BA4,
236 0x0BA8...0x0BAA,
237 0x0BAE...0x0BB5,
238 0x0BB7...0x0BB9,
239 0x0BBE...0x0BC2,
240 0x0BC6...0x0BC8,
241 0x0BCA...0x0BCD,
242
243 // Telugu
244 0x0C01...0x0C03,
245 0x0C05...0x0C0C,
246 0x0C0E...0x0C10,
247 0x0C12...0x0C28,
248 0x0C2A...0x0C33,
249 0x0C35...0x0C39,
250 0x0C3E...0x0C44,
251 0x0C46...0x0C48,
252 0x0C4A...0x0C4D,
253 0x0C60...0x0C61,
254
255 // Kannada
256 0x0C82...0x0C83,
257 0x0C85...0x0C8C,
258 0x0C8E...0x0C90,
259 0x0C92...0x0CA8,
260 0x0CAA...0x0CB3,
261 0x0CB5...0x0CB9,
262 0x0CBE...0x0CC4,
263 0x0CC6...0x0CC8,
264 0x0CCA...0x0CCD,
265 0x0CDE,
266 0x0CE0...0x0CE1,
267
268 // Malayalam
269 0x0D02...0x0D03,
270 0x0D05...0x0D0C,
271 0x0D0E...0x0D10,
272 0x0D12...0x0D28,
273 0x0D2A...0x0D39,
274 0x0D3E...0x0D43,
275 0x0D46...0x0D48,
276 0x0D4A...0x0D4D,
277 0x0D60...0x0D61,
278
279 // Thai (excluding digits 0x0E50...0x0E59; originally 0x0E01...0x0E3A and 0x0E40...0x0E5B
280 0x0E01...0x0E3A,
281 0x0E40...0x0E4F,
282 0x0E5A...0x0E5B,
283
284 // Lao
285 0x0E81...0x0E82,
286 0x0E84,
287 0x0E87...0x0E88,
288 0x0E8A,
289 0x0E8D,
290 0x0E94...0x0E97,
291 0x0E99...0x0E9F,
292 0x0EA1...0x0EA3,
293 0x0EA5,
294 0x0EA7,
295 0x0EAA...0x0EAB,
296 0x0EAD...0x0EAE,
297 0x0EB0...0x0EB9,
298 0x0EBB...0x0EBD,
299 0x0EC0...0x0EC4,
300 0x0EC6,
301 0x0EC8...0x0ECD,
302 0x0EDC...0x0EDD,
303
304 // Tibetan
305 0x0F00,
306 0x0F18...0x0F19,
307 0x0F35,
308 0x0F37,
309 0x0F39,
310 0x0F3E...0x0F47,
311 0x0F49...0x0F69,
312 0x0F71...0x0F84,
313 0x0F86...0x0F8B,
314 0x0F90...0x0F95,
315 0x0F97,
316 0x0F99...0x0FAD,
317 0x0FB1...0x0FB7,
318 0x0FB9,
319
320 // Georgian
321 0x10A0...0x10C5,
322 0x10D0...0x10F6,
323
324 // Hiragana
325 0x3041...0x3093,
326 0x309B...0x309C,
327
328 // Katakana
329 0x30A1...0x30F6,
330 0x30FB...0x30FC,
331
332 // Bopomofo
333 0x3105...0x312C,
334
335 // CJK Unified Ideographs
336 0x4E00...0x9FA5,
337
338 // Hangul
339 0xAC00...0xD7A3,
340
341 // Digits
342 0x0660...0x0669,
343 0x06F0...0x06F9,
344 0x0966...0x096F,
345 0x09E6...0x09EF,
346 0x0A66...0x0A6F,
347 0x0AE6...0x0AEF,
348 0x0B66...0x0B6F,
349 0x0BE7...0x0BEF,
350 0x0C66...0x0C6F,
351 0x0CE6...0x0CEF,
352 0x0D66...0x0D6F,
353 0x0E50...0x0E59,
354 0x0ED0...0x0ED9,
355 0x0F20...0x0F33,
356
357 // Special characters
358 0x00B5,
359 0x00B7,
360 0x02B0...0x02B8,
361 0x02BB,
362 0x02BD...0x02C1,
363 0x02D0...0x02D1,
364 0x02E0...0x02E4,
365 0x037A,
366 0x0559,
367 0x093D,
368 0x0B3D,
369 0x1FBE,
370 0x203F...0x2040,
371 0x2102,
372 0x2107,
373 0x210A...0x2113,
374 0x2115,
375 0x2118...0x211D,
376 0x2124,
377 0x2126,
378 0x2128,
379 0x212A...0x2131,
380 0x2133...0x2138,
381 0x2160...0x2182,
382 0x3005...0x3007,
383 0x3021...0x3029,
384 => true,
385 else => false,
386 };
387}
388
389/// C11 standard Annex D
390pub fn isC11DisallowedInitialIdChar(codepoint: u21) bool {
391 assert(codepoint > 0x7F);
392 return switch (codepoint) {
393 0x0300...0x036F,
394 0x1DC0...0x1DFF,
395 0x20D0...0x20FF,
396 0xFE20...0xFE2F,
397 => true,
398 else => false,
399 };
400}
401
402/// These are "digit" characters; C99 disallows them as the first
403/// character of an identifier
404pub fn isC99DisallowedInitialIDChar(codepoint: u21) bool {
405 assert(codepoint > 0x7F);
406 return switch (codepoint) {
407 0x0660...0x0669,
408 0x06F0...0x06F9,
409 0x0966...0x096F,
410 0x09E6...0x09EF,
411 0x0A66...0x0A6F,
412 0x0AE6...0x0AEF,
413 0x0B66...0x0B6F,
414 0x0BE7...0x0BEF,
415 0x0C66...0x0C6F,
416 0x0CE6...0x0CEF,
417 0x0D66...0x0D6F,
418 0x0E50...0x0E59,
419 0x0ED0...0x0ED9,
420 0x0F20...0x0F33,
421 => true,
422 else => false,
423 };
424}
425
426pub fn isInvisible(codepoint: u21) bool {
427 assert(codepoint > 0x7F);
428 return switch (codepoint) {
429 0x00ad, // SOFT HYPHEN
430 0x200b, // ZERO WIDTH SPACE
431 0x200c, // ZERO WIDTH NON-JOINER
432 0x200d, // ZERO WIDTH JOINER
433 0x2060, // WORD JOINER
434 0x2061, // FUNCTION APPLICATION
435 0x2062, // INVISIBLE TIMES
436 0x2063, // INVISIBLE SEPARATOR
437 0x2064, // INVISIBLE PLUS
438 0xfeff, // ZERO WIDTH NO-BREAK SPACE
439 => true,
440 else => false,
441 };
442}
443
444/// Checks for identifier characters which resemble non-identifier characters
445pub fn homoglyph(codepoint: u21) ?u21 {
446 assert(codepoint > 0x7F);
447 return switch (codepoint) {
448 0x01c3 => '!', // LATIN LETTER RETROFLEX CLICK
449 0x037e => ';', // GREEK QUESTION MARK
450 0x2212 => '-', // MINUS SIGN
451 0x2215 => '/', // DIVISION SLASH
452 0x2216 => '\\', // SET MINUS
453 0x2217 => '*', // ASTERISK OPERATOR
454 0x2223 => '|', // DIVIDES
455 0x2227 => '^', // LOGICAL AND
456 0x2236 => ':', // RATIO
457 0x223c => '~', // TILDE OPERATOR
458 0xa789 => ':', // MODIFIER LETTER COLON
459 0xff01 => '!', // FULLWIDTH EXCLAMATION MARK
460 0xff03 => '#', // FULLWIDTH NUMBER SIGN
461 0xff04 => '$', // FULLWIDTH DOLLAR SIGN
462 0xff05 => '%', // FULLWIDTH PERCENT SIGN
463 0xff06 => '&', // FULLWIDTH AMPERSAND
464 0xff08 => '(', // FULLWIDTH LEFT PARENTHESIS
465 0xff09 => ')', // FULLWIDTH RIGHT PARENTHESIS
466 0xff0a => '*', // FULLWIDTH ASTERISK
467 0xff0b => '+', // FULLWIDTH ASTERISK
468 0xff0c => ',', // FULLWIDTH COMMA
469 0xff0d => '-', // FULLWIDTH HYPHEN-MINUS
470 0xff0e => '.', // FULLWIDTH FULL STOP
471 0xff0f => '/', // FULLWIDTH SOLIDUS
472 0xff1a => ':', // FULLWIDTH COLON
473 0xff1b => ';', // FULLWIDTH SEMICOLON
474 0xff1c => '<', // FULLWIDTH LESS-THAN SIGN
475 0xff1d => '=', // FULLWIDTH EQUALS SIGN
476 0xff1e => '>', // FULLWIDTH GREATER-THAN SIGN
477 0xff1f => '?', // FULLWIDTH QUESTION MARK
478 0xff20 => '@', // FULLWIDTH COMMERCIAL AT
479 0xff3b => '[', // FULLWIDTH LEFT SQUARE BRACKET
480 0xff3c => '\\', // FULLWIDTH REVERSE SOLIDUS
481 0xff3d => ']', // FULLWIDTH RIGHT SQUARE BRACKET
482 0xff3e => '^', // FULLWIDTH CIRCUMFLEX ACCENT
483 0xff5b => '{', // FULLWIDTH LEFT CURLY BRACKET
484 0xff5c => '|', // FULLWIDTH VERTICAL LINE
485 0xff5d => '}', // FULLWIDTH RIGHT CURLY BRACKET
486 0xff5e => '~', // FULLWIDTH TILDE
487 else => null,
488 };
489}
490
491pub fn isXidStart(c: u21) bool {
492 assert(c > 0x7F);
493 const idx = c / 8 / tables.chunk;
494 const chunk: usize = if (idx < tables.trie_start.len) tables.trie_start[idx] else 0;
495 const offset = chunk * tables.chunk / 2 + c / 8 % tables.chunk;
496 return (tables.leaf[offset] >> (@as(u3, @intCast(c % 8)))) & 1 != 0;
497}
498
499pub fn isXidContinue(c: u21) bool {
500 assert(c > 0x7F);
501 const idx = c / 8 / tables.chunk;
502 const chunk: usize = if (idx < tables.trie_continue.len) tables.trie_continue[idx] else 0;
503 const offset = chunk * tables.chunk / 2 + c / 8 % tables.chunk;
504 return (tables.leaf[offset] >> (@as(u3, @intCast(c % 8)))) & 1 != 0;
505}
506
507test "isXidStart / isXidContinue panic check" {
508 const std = @import("std");
509 for (0x80..0x110000) |i| {
510 const c: u21 = @intCast(i);
511 if (std.unicode.utf8ValidCodepoint(c)) {
512 _ = isXidStart(c);
513 _ = isXidContinue(c);
514 }
515 }
516}
517
518test isXidStart {
519 const std = @import("std");
520 try std.testing.expect(!isXidStart('᠑'));
521 try std.testing.expect(!isXidStart('™'));
522 try std.testing.expect(!isXidStart('£'));
523 try std.testing.expect(!isXidStart('\u{1f914}')); // 🤔
524}
525
526test isXidContinue {
527 const std = @import("std");
528 try std.testing.expect(isXidContinue('᠑'));
529 try std.testing.expect(!isXidContinue('™'));
530 try std.testing.expect(!isXidContinue('£'));
531 try std.testing.expect(!isXidContinue('\u{1f914}')); // 🤔
532}
533
534pub const NfcQuickCheck = enum { no, maybe, yes };
535
536pub fn isNormalized(codepoint: u21) NfcQuickCheck {
537 return switch (codepoint) {
538 0x0340...0x0341,
539 0x0343...0x0344,
540 0x0374,
541 0x037E,
542 0x0387,
543 0x0958...0x095F,
544 0x09DC...0x09DD,
545 0x09DF,
546 0x0A33,
547 0x0A36,
548 0x0A59...0x0A5B,
549 0x0A5E,
550 0x0B5C...0x0B5D,
551 0x0F43,
552 0x0F4D,
553 0x0F52,
554 0x0F57,
555 0x0F5C,
556 0x0F69,
557 0x0F73,
558 0x0F75...0x0F76,
559 0x0F78,
560 0x0F81,
561 0x0F93,
562 0x0F9D,
563 0x0FA2,
564 0x0FA7,
565 0x0FAC,
566 0x0FB9,
567 0x1F71,
568 0x1F73,
569 0x1F75,
570 0x1F77,
571 0x1F79,
572 0x1F7B,
573 0x1F7D,
574 0x1FBB,
575 0x1FBE,
576 0x1FC9,
577 0x1FCB,
578 0x1FD3,
579 0x1FDB,
580 0x1FE3,
581 0x1FEB,
582 0x1FEE...0x1FEF,
583 0x1FF9,
584 0x1FFB,
585 0x1FFD,
586 0x2000...0x2001,
587 0x2126,
588 0x212A...0x212B,
589 0x2329,
590 0x232A,
591 0x2ADC,
592 0xF900...0xFA0D,
593 0xFA10,
594 0xFA12,
595 0xFA15...0xFA1E,
596 0xFA20,
597 0xFA22,
598 0xFA25...0xFA26,
599 0xFA2A...0xFA6D,
600 0xFA70...0xFAD9,
601 0xFB1D,
602 0xFB1F,
603 0xFB2A...0xFB36,
604 0xFB38...0xFB3C,
605 0xFB3E,
606 0xFB40...0xFB41,
607 0xFB43...0xFB44,
608 0xFB46...0xFB4E,
609 0x1D15E...0x1D164,
610 0x1D1BB...0x1D1C0,
611 0x2F800...0x2FA1D,
612 => .no,
613 0x0300...0x0304,
614 0x0306...0x030C,
615 0x030F,
616 0x0311,
617 0x0313...0x0314,
618 0x031B,
619 0x0323...0x0328,
620 0x032D...0x032E,
621 0x0330...0x0331,
622 0x0338,
623 0x0342,
624 0x0345,
625 0x0653...0x0655,
626 0x093C,
627 0x09BE,
628 0x09D7,
629 0x0B3E,
630 0x0B56,
631 0x0B57,
632 0x0BBE,
633 0x0BD7,
634 0x0C56,
635 0x0CC2,
636 0x0CD5...0x0CD6,
637 0x0D3E,
638 0x0D57,
639 0x0DCA,
640 0x0DCF,
641 0x0DDF,
642 0x102E,
643 0x1161...0x1175,
644 0x11A8...0x11C2,
645 0x1B35,
646 0x3099...0x309A,
647 0x110BA,
648 0x11127,
649 0x1133E,
650 0x11357,
651 0x114B0,
652 0x114BA,
653 0x114BD,
654 0x115AF,
655 => .maybe,
656 else => .yes,
657 };
658}
659
660pub const CanonicalCombiningClass = enum(u8) {
661 not_reordered = 0,
662 overlay = 1,
663 han_reading = 6,
664 nukta = 7,
665 kana_voicing = 8,
666 virama = 9,
667 ccc10 = 10,
668 ccc11 = 11,
669 ccc12 = 12,
670 ccc13 = 13,
671 ccc14 = 14,
672 ccc15 = 15,
673 ccc16 = 16,
674 ccc17 = 17,
675 ccc18 = 18,
676 ccc19 = 19,
677 ccc20 = 20,
678 ccc21 = 21,
679 ccc22 = 22,
680 ccc23 = 23,
681 ccc24 = 24,
682 ccc25 = 25,
683 ccc26 = 26,
684 ccc27 = 27,
685 ccc28 = 28,
686 ccc29 = 29,
687 ccc30 = 30,
688 ccc31 = 31,
689 ccc32 = 32,
690 ccc33 = 33,
691 ccc34 = 34,
692 ccc35 = 35,
693 ccc36 = 36,
694 ccc84 = 84,
695 ccc91 = 91,
696 ccc103 = 103,
697 ccc107 = 107,
698 ccc118 = 118,
699 ccc122 = 122,
700 ccc129 = 129,
701 ccc130 = 130,
702 ccc132 = 132,
703 attached_below = 202,
704 attached_above = 214,
705 attached_above_right = 216,
706 below_left = 218,
707 below = 220,
708 below_right = 222,
709 left = 224,
710 right = 226,
711 above_left = 228,
712 above = 230,
713 above_right = 232,
714 double_below = 233,
715 double_above = 234,
716 iota_subscript = 240,
717};
718
719pub fn getCanonicalClass(codepoint: u21) CanonicalCombiningClass {
720 return switch (codepoint) {
721 0x300...0x314 => .above,
722 0x315...0x315 => .above_right,
723 0x316...0x319 => .below,
724 0x31A...0x31A => .above_right,
725 0x31B...0x31B => .attached_above_right,
726 0x31C...0x320 => .below,
727 0x321...0x322 => .attached_below,
728 0x323...0x326 => .below,
729 0x327...0x328 => .attached_below,
730 0x329...0x333 => .below,
731 0x334...0x338 => .overlay,
732 0x339...0x33C => .below,
733 0x33D...0x344 => .above,
734 0x345...0x345 => .iota_subscript,
735 0x346...0x346 => .above,
736 0x347...0x349 => .below,
737 0x34A...0x34C => .above,
738 0x34D...0x34E => .below,
739 0x350...0x352 => .above,
740 0x353...0x356 => .below,
741 0x357...0x357 => .above,
742 0x358...0x358 => .above_right,
743 0x359...0x35A => .below,
744 0x35B...0x35B => .above,
745 0x35C...0x35C => .double_below,
746 0x35D...0x35E => .double_above,
747 0x35F...0x35F => .double_below,
748 0x360...0x361 => .double_above,
749 0x362...0x362 => .double_below,
750 0x363...0x36F => .above,
751 0x483...0x487 => .above,
752 0x591...0x591 => .below,
753 0x592...0x595 => .above,
754 0x596...0x596 => .below,
755 0x597...0x599 => .above,
756 0x59A...0x59A => .below_right,
757 0x59B...0x59B => .below,
758 0x59C...0x5A1 => .above,
759 0x5A2...0x5A7 => .below,
760 0x5A8...0x5A9 => .above,
761 0x5AA...0x5AA => .below,
762 0x5AB...0x5AC => .above,
763 0x5AD...0x5AD => .below_right,
764 0x5AE...0x5AE => .above_left,
765 0x5AF...0x5AF => .above,
766 0x5B0...0x5B0 => .ccc10,
767 0x5B1...0x5B1 => .ccc11,
768 0x5B2...0x5B2 => .ccc12,
769 0x5B3...0x5B3 => .ccc13,
770 0x5B4...0x5B4 => .ccc14,
771 0x5B5...0x5B5 => .ccc15,
772 0x5B6...0x5B6 => .ccc16,
773 0x5B7...0x5B7 => .ccc17,
774 0x5B8...0x5B8 => .ccc18,
775 0x5B9...0x5BA => .ccc19,
776 0x5BB...0x5BB => .ccc20,
777 0x5BC...0x5BC => .ccc21,
778 0x5BD...0x5BD => .ccc22,
779 0x5BF...0x5BF => .ccc23,
780 0x5C1...0x5C1 => .ccc24,
781 0x5C2...0x5C2 => .ccc25,
782 0x5C4...0x5C4 => .above,
783 0x5C5...0x5C5 => .below,
784 0x5C7...0x5C7 => .ccc18,
785 0x610...0x617 => .above,
786 0x618...0x618 => .ccc30,
787 0x619...0x619 => .ccc31,
788 0x61A...0x61A => .ccc32,
789 0x64B...0x64B => .ccc27,
790 0x64C...0x64C => .ccc28,
791 0x64D...0x64D => .ccc29,
792 0x64E...0x64E => .ccc30,
793 0x64F...0x64F => .ccc31,
794 0x650...0x650 => .ccc32,
795 0x651...0x651 => .ccc33,
796 0x652...0x652 => .ccc34,
797 0x653...0x654 => .above,
798 0x655...0x656 => .below,
799 0x657...0x65B => .above,
800 0x65C...0x65C => .below,
801 0x65D...0x65E => .above,
802 0x65F...0x65F => .below,
803 0x670...0x670 => .ccc35,
804 0x6D6...0x6DC => .above,
805 0x6DF...0x6E2 => .above,
806 0x6E3...0x6E3 => .below,
807 0x6E4...0x6E4 => .above,
808 0x6E7...0x6E8 => .above,
809 0x6EA...0x6EA => .below,
810 0x6EB...0x6EC => .above,
811 0x6ED...0x6ED => .below,
812 0x711...0x711 => .ccc36,
813 0x730...0x730 => .above,
814 0x731...0x731 => .below,
815 0x732...0x733 => .above,
816 0x734...0x734 => .below,
817 0x735...0x736 => .above,
818 0x737...0x739 => .below,
819 0x73A...0x73A => .above,
820 0x73B...0x73C => .below,
821 0x73D...0x73D => .above,
822 0x73E...0x73E => .below,
823 0x73F...0x741 => .above,
824 0x742...0x742 => .below,
825 0x743...0x743 => .above,
826 0x744...0x744 => .below,
827 0x745...0x745 => .above,
828 0x746...0x746 => .below,
829 0x747...0x747 => .above,
830 0x748...0x748 => .below,
831 0x749...0x74A => .above,
832 0x7EB...0x7F1 => .above,
833 0x7F2...0x7F2 => .below,
834 0x7F3...0x7F3 => .above,
835 0x7FD...0x7FD => .below,
836 0x816...0x819 => .above,
837 0x81B...0x823 => .above,
838 0x825...0x827 => .above,
839 0x829...0x82D => .above,
840 0x859...0x85B => .below,
841 0x898...0x898 => .above,
842 0x899...0x89B => .below,
843 0x89C...0x89F => .above,
844 0x8CA...0x8CE => .above,
845 0x8CF...0x8D3 => .below,
846 0x8D4...0x8E1 => .above,
847 0x8E3...0x8E3 => .below,
848 0x8E4...0x8E5 => .above,
849 0x8E6...0x8E6 => .below,
850 0x8E7...0x8E8 => .above,
851 0x8E9...0x8E9 => .below,
852 0x8EA...0x8EC => .above,
853 0x8ED...0x8EF => .below,
854 0x8F0...0x8F0 => .ccc27,
855 0x8F1...0x8F1 => .ccc28,
856 0x8F2...0x8F2 => .ccc29,
857 0x8F3...0x8F5 => .above,
858 0x8F6...0x8F6 => .below,
859 0x8F7...0x8F8 => .above,
860 0x8F9...0x8FA => .below,
861 0x8FB...0x8FF => .above,
862 0x93C...0x93C => .nukta,
863 0x94D...0x94D => .virama,
864 0x951...0x951 => .above,
865 0x952...0x952 => .below,
866 0x953...0x954 => .above,
867 0x9BC...0x9BC => .nukta,
868 0x9CD...0x9CD => .virama,
869 0x9FE...0x9FE => .above,
870 0xA3C...0xA3C => .nukta,
871 0xA4D...0xA4D => .virama,
872 0xABC...0xABC => .nukta,
873 0xACD...0xACD => .virama,
874 0xB3C...0xB3C => .nukta,
875 0xB4D...0xB4D => .virama,
876 0xBCD...0xBCD => .virama,
877 0xC3C...0xC3C => .nukta,
878 0xC4D...0xC4D => .virama,
879 0xC55...0xC55 => .ccc84,
880 0xC56...0xC56 => .ccc91,
881 0xCBC...0xCBC => .nukta,
882 0xCCD...0xCCD => .virama,
883 0xD3B...0xD3C => .virama,
884 0xD4D...0xD4D => .virama,
885 0xDCA...0xDCA => .virama,
886 0xE38...0xE39 => .ccc103,
887 0xE3A...0xE3A => .virama,
888 0xE48...0xE4B => .ccc107,
889 0xEB8...0xEB9 => .ccc118,
890 0xEBA...0xEBA => .virama,
891 0xEC8...0xECB => .ccc122,
892 0xF18...0xF19 => .below,
893 0xF35...0xF35 => .below,
894 0xF37...0xF37 => .below,
895 0xF39...0xF39 => .attached_above_right,
896 0xF71...0xF71 => .ccc129,
897 0xF72...0xF72 => .ccc130,
898 0xF74...0xF74 => .ccc132,
899 0xF7A...0xF7D => .ccc130,
900 0xF80...0xF80 => .ccc130,
901 0xF82...0xF83 => .above,
902 0xF84...0xF84 => .virama,
903 0xF86...0xF87 => .above,
904 0xFC6...0xFC6 => .below,
905 0x1037...0x1037 => .nukta,
906 0x1039...0x103A => .virama,
907 0x108D...0x108D => .below,
908 0x135D...0x135F => .above,
909 0x1714...0x1715 => .virama,
910 0x1734...0x1734 => .virama,
911 0x17D2...0x17D2 => .virama,
912 0x17DD...0x17DD => .above,
913 0x18A9...0x18A9 => .above_left,
914 0x1939...0x1939 => .below_right,
915 0x193A...0x193A => .above,
916 0x193B...0x193B => .below,
917 0x1A17...0x1A17 => .above,
918 0x1A18...0x1A18 => .below,
919 0x1A60...0x1A60 => .virama,
920 0x1A75...0x1A7C => .above,
921 0x1A7F...0x1A7F => .below,
922 0x1AB0...0x1AB4 => .above,
923 0x1AB5...0x1ABA => .below,
924 0x1ABB...0x1ABC => .above,
925 0x1ABD...0x1ABD => .below,
926 0x1ABF...0x1AC0 => .below,
927 0x1AC1...0x1AC2 => .above,
928 0x1AC3...0x1AC4 => .below,
929 0x1AC5...0x1AC9 => .above,
930 0x1ACA...0x1ACA => .below,
931 0x1ACB...0x1ACE => .above,
932 0x1B34...0x1B34 => .nukta,
933 0x1B44...0x1B44 => .virama,
934 0x1B6B...0x1B6B => .above,
935 0x1B6C...0x1B6C => .below,
936 0x1B6D...0x1B73 => .above,
937 0x1BAA...0x1BAB => .virama,
938 0x1BE6...0x1BE6 => .nukta,
939 0x1BF2...0x1BF3 => .virama,
940 0x1C37...0x1C37 => .nukta,
941 0x1CD0...0x1CD2 => .above,
942 0x1CD4...0x1CD4 => .overlay,
943 0x1CD5...0x1CD9 => .below,
944 0x1CDA...0x1CDB => .above,
945 0x1CDC...0x1CDF => .below,
946 0x1CE0...0x1CE0 => .above,
947 0x1CE2...0x1CE8 => .overlay,
948 0x1CED...0x1CED => .below,
949 0x1CF4...0x1CF4 => .above,
950 0x1CF8...0x1CF9 => .above,
951 0x1DC0...0x1DC1 => .above,
952 0x1DC2...0x1DC2 => .below,
953 0x1DC3...0x1DC9 => .above,
954 0x1DCA...0x1DCA => .below,
955 0x1DCB...0x1DCC => .above,
956 0x1DCD...0x1DCD => .double_above,
957 0x1DCE...0x1DCE => .attached_above,
958 0x1DCF...0x1DCF => .below,
959 0x1DD0...0x1DD0 => .attached_below,
960 0x1DD1...0x1DF5 => .above,
961 0x1DF6...0x1DF6 => .above_right,
962 0x1DF7...0x1DF8 => .above_left,
963 0x1DF9...0x1DF9 => .below,
964 0x1DFA...0x1DFA => .below_left,
965 0x1DFB...0x1DFB => .above,
966 0x1DFC...0x1DFC => .double_below,
967 0x1DFD...0x1DFD => .below,
968 0x1DFE...0x1DFE => .above,
969 0x1DFF...0x1DFF => .below,
970 0x20D0...0x20D1 => .above,
971 0x20D2...0x20D3 => .overlay,
972 0x20D4...0x20D7 => .above,
973 0x20D8...0x20DA => .overlay,
974 0x20DB...0x20DC => .above,
975 0x20E1...0x20E1 => .above,
976 0x20E5...0x20E6 => .overlay,
977 0x20E7...0x20E7 => .above,
978 0x20E8...0x20E8 => .below,
979 0x20E9...0x20E9 => .above,
980 0x20EA...0x20EB => .overlay,
981 0x20EC...0x20EF => .below,
982 0x20F0...0x20F0 => .above,
983 0x2CEF...0x2CF1 => .above,
984 0x2D7F...0x2D7F => .virama,
985 0x2DE0...0x2DFF => .above,
986 0x302A...0x302A => .below_left,
987 0x302B...0x302B => .above_left,
988 0x302C...0x302C => .above_right,
989 0x302D...0x302D => .below_right,
990 0x302E...0x302F => .left,
991 0x3099...0x309A => .kana_voicing,
992 0xA66F...0xA66F => .above,
993 0xA674...0xA67D => .above,
994 0xA69E...0xA69F => .above,
995 0xA6F0...0xA6F1 => .above,
996 0xA806...0xA806 => .virama,
997 0xA82C...0xA82C => .virama,
998 0xA8C4...0xA8C4 => .virama,
999 0xA8E0...0xA8F1 => .above,
1000 0xA92B...0xA92D => .below,
1001 0xA953...0xA953 => .virama,
1002 0xA9B3...0xA9B3 => .nukta,
1003 0xA9C0...0xA9C0 => .virama,
1004 0xAAB0...0xAAB0 => .above,
1005 0xAAB2...0xAAB3 => .above,
1006 0xAAB4...0xAAB4 => .below,
1007 0xAAB7...0xAAB8 => .above,
1008 0xAABE...0xAABF => .above,
1009 0xAAC1...0xAAC1 => .above,
1010 0xAAF6...0xAAF6 => .virama,
1011 0xABED...0xABED => .virama,
1012 0xFB1E...0xFB1E => .ccc26,
1013 0xFE20...0xFE26 => .above,
1014 0xFE27...0xFE2D => .below,
1015 0xFE2E...0xFE2F => .above,
1016 0x101FD...0x101FD => .below,
1017 0x102E0...0x102E0 => .below,
1018 0x10376...0x1037A => .above,
1019 0x10A0D...0x10A0D => .below,
1020 0x10A0F...0x10A0F => .above,
1021 0x10A38...0x10A38 => .above,
1022 0x10A39...0x10A39 => .overlay,
1023 0x10A3A...0x10A3A => .below,
1024 0x10A3F...0x10A3F => .virama,
1025 0x10AE5...0x10AE5 => .above,
1026 0x10AE6...0x10AE6 => .below,
1027 0x10D24...0x10D27 => .above,
1028 0x10EAB...0x10EAC => .above,
1029 0x10EFD...0x10EFF => .below,
1030 0x10F46...0x10F47 => .below,
1031 0x10F48...0x10F4A => .above,
1032 0x10F4B...0x10F4B => .below,
1033 0x10F4C...0x10F4C => .above,
1034 0x10F4D...0x10F50 => .below,
1035 0x10F82...0x10F82 => .above,
1036 0x10F83...0x10F83 => .below,
1037 0x10F84...0x10F84 => .above,
1038 0x10F85...0x10F85 => .below,
1039 0x11046...0x11046 => .virama,
1040 0x11070...0x11070 => .virama,
1041 0x1107F...0x1107F => .virama,
1042 0x110B9...0x110B9 => .virama,
1043 0x110BA...0x110BA => .nukta,
1044 0x11100...0x11102 => .above,
1045 0x11133...0x11134 => .virama,
1046 0x11173...0x11173 => .nukta,
1047 0x111C0...0x111C0 => .virama,
1048 0x111CA...0x111CA => .nukta,
1049 0x11235...0x11235 => .virama,
1050 0x11236...0x11236 => .nukta,
1051 0x112E9...0x112E9 => .nukta,
1052 0x112EA...0x112EA => .virama,
1053 0x1133B...0x1133C => .nukta,
1054 0x1134D...0x1134D => .virama,
1055 0x11366...0x1136C => .above,
1056 0x11370...0x11374 => .above,
1057 0x11442...0x11442 => .virama,
1058 0x11446...0x11446 => .nukta,
1059 0x1145E...0x1145E => .above,
1060 0x114C2...0x114C2 => .virama,
1061 0x114C3...0x114C3 => .nukta,
1062 0x115BF...0x115BF => .virama,
1063 0x115C0...0x115C0 => .nukta,
1064 0x1163F...0x1163F => .virama,
1065 0x116B6...0x116B6 => .virama,
1066 0x116B7...0x116B7 => .nukta,
1067 0x1172B...0x1172B => .virama,
1068 0x11839...0x11839 => .virama,
1069 0x1183A...0x1183A => .nukta,
1070 0x1193D...0x1193E => .virama,
1071 0x11943...0x11943 => .nukta,
1072 0x119E0...0x119E0 => .virama,
1073 0x11A34...0x11A34 => .virama,
1074 0x11A47...0x11A47 => .virama,
1075 0x11A99...0x11A99 => .virama,
1076 0x11C3F...0x11C3F => .virama,
1077 0x11D42...0x11D42 => .nukta,
1078 0x11D44...0x11D45 => .virama,
1079 0x11D97...0x11D97 => .virama,
1080 0x11F41...0x11F42 => .virama,
1081 0x16AF0...0x16AF4 => .overlay,
1082 0x16B30...0x16B36 => .above,
1083 0x16FF0...0x16FF1 => .han_reading,
1084 0x1BC9E...0x1BC9E => .overlay,
1085 0x1D165...0x1D166 => .attached_above_right,
1086 0x1D167...0x1D169 => .overlay,
1087 0x1D16D...0x1D16D => .right,
1088 0x1D16E...0x1D172 => .attached_above_right,
1089 0x1D17B...0x1D182 => .below,
1090 0x1D185...0x1D189 => .above,
1091 0x1D18A...0x1D18B => .below,
1092 0x1D1AA...0x1D1AD => .above,
1093 0x1D242...0x1D244 => .above,
1094 0x1E000...0x1E006 => .above,
1095 0x1E008...0x1E018 => .above,
1096 0x1E01B...0x1E021 => .above,
1097 0x1E023...0x1E024 => .above,
1098 0x1E026...0x1E02A => .above,
1099 0x1E08F...0x1E08F => .above,
1100 0x1E130...0x1E136 => .above,
1101 0x1E2AE...0x1E2AE => .above,
1102 0x1E2EC...0x1E2EF => .above,
1103 0x1E4EC...0x1E4ED => .above_right,
1104 0x1E4EE...0x1E4EE => .below,
1105 0x1E4EF...0x1E4EF => .above,
1106 0x1E8D0...0x1E8D6 => .below,
1107 0x1E944...0x1E949 => .above,
1108 0x1E94A...0x1E94A => .nukta,
1109 else => .not_reordered,
1110 };
1111}
lib/compiler/aro/aro/char_info/identifier_tables.zig deleted-627
...@@ -1,627 +0,0 @@
1//! Adapted from the `unicode-ident` crate: https://github.com/dtolnay/unicode-ident
2//! and Unicode Standard Annex #31 https://www.unicode.org/reports/tr31/
3//! Licensed under the MIT License and the Unicode license
4
5pub const chunk = 64;
6
7pub const trie_start: [402]u8 align(8) = .{
8 0x04, 0x0B, 0x0F, 0x13, 0x17, 0x1B, 0x1F, 0x23, 0x27, 0x2D, 0x31, 0x34, 0x38, 0x3C, 0x40, 0x02,
9 0x45, 0x00, 0x00, 0x00, 0x00, 0x00, 0x49, 0x00, 0x4D, 0x00, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
10 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x06, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
11 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
12 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
13 0x05, 0x05, 0x51, 0x54, 0x58, 0x5C, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
14 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x09, 0x00, 0x00, 0x00, 0x00,
15 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x60, 0x64, 0x66,
16 0x6A, 0x6E, 0x72, 0x28, 0x76, 0x78, 0x7C, 0x80, 0x84, 0x88, 0x8C, 0x90, 0x94, 0x98, 0x9E, 0xA2,
17 0x05, 0x2B, 0xA6, 0x00, 0x00, 0x00, 0x00, 0x99, 0x05, 0x05, 0xA8, 0x00, 0x00, 0x00, 0x00, 0x00,
18 0x00, 0x00, 0x05, 0xAE, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
19 0x00, 0x00, 0x00, 0x00, 0x05, 0xB1, 0x00, 0xB5, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
20 0x05, 0x05, 0x05, 0x32, 0x05, 0x05, 0xB9, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
21 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x9C, 0x43, 0xBB, 0x00, 0x00, 0x00, 0x00, 0xBE, 0x00,
22 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC6, 0xC8, 0x00, 0x00, 0x00, 0xAF,
23 0xCE, 0xD2, 0xD6, 0xBC, 0xDA, 0x00, 0x00, 0xDE, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
24 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
25 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
26 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
27 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
28 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
29 0x05, 0x05, 0x05, 0xE0, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x52, 0xE3, 0x05, 0x05, 0x05,
30 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0xE6, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
31 0x05, 0x05, 0x05, 0x05, 0x05, 0xE1, 0x05, 0xE9, 0x00, 0x00, 0x00, 0x00, 0x05, 0xEB, 0x00, 0x00,
32 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0xE4, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
33 0x05, 0xE7,
34};
35
36pub const trie_continue: [1793]u8 align(8) = .{
37 0x08, 0x0D, 0x11, 0x15, 0x19, 0x1D, 0x21, 0x25, 0x2A, 0x2F, 0x31, 0x36, 0x3A, 0x3E, 0x42, 0x02,
38 0x47, 0x00, 0x00, 0x00, 0x00, 0x00, 0x4B, 0x00, 0x4F, 0x00, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
39 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x06, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
40 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
41 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
42 0x05, 0x05, 0x51, 0x56, 0x5A, 0x5E, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
43 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x09, 0x00, 0x00, 0x00, 0x00,
44 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x62, 0x64, 0x68,
45 0x6C, 0x70, 0x74, 0x28, 0x76, 0x7A, 0x7E, 0x82, 0x86, 0x8A, 0x8E, 0x92, 0x96, 0x9B, 0xA0, 0xA4,
46 0x05, 0x2B, 0xA6, 0x00, 0x00, 0x00, 0x00, 0x99, 0x05, 0x05, 0xAB, 0x00, 0x00, 0x00, 0x00, 0x00,
47 0x00, 0x00, 0x05, 0xAE, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
48 0x00, 0x00, 0x00, 0x00, 0x05, 0xB3, 0x00, 0xB7, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
49 0x05, 0x05, 0x05, 0x32, 0x05, 0x05, 0xB9, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
50 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x9C, 0x43, 0xBB, 0x00, 0x00, 0x00, 0x00, 0xC1, 0x00,
51 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA9, 0xAC, 0xC4, 0xC6, 0xCA, 0x00, 0xCC, 0x00, 0xAF,
52 0xD0, 0xD4, 0xD8, 0xBC, 0xDC, 0x00, 0x00, 0xDE, 0x00, 0x00, 0x00, 0x00, 0x00, 0xBF, 0x00, 0x00,
53 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
54 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
55 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
56 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
57 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
58 0x05, 0x05, 0x05, 0xE0, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x52, 0xE3, 0x05, 0x05, 0x05,
59 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0xE6, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
60 0x05, 0x05, 0x05, 0x05, 0x05, 0xE1, 0x05, 0xE9, 0x00, 0x00, 0x00, 0x00, 0x05, 0xEB, 0x00, 0x00,
61 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0xE4, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
62 0x05, 0xE7, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
63 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
64 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
65 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
66 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
67 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
68 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
69 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
70 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
71 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
72 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
73 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
74 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
75 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
76 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
77 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
78 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
79 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
80 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
81 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
82 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
83 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
84 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
85 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
86 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
87 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
88 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
89 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
90 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
91 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
92 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
93 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
94 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
95 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
96 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
97 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
98 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
99 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
100 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
101 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
102 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
103 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
104 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
105 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
106 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
107 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
108 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
109 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
110 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
111 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
112 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
113 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
114 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
115 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
116 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
117 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
118 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
119 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
120 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
121 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
122 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
123 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
124 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
125 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
126 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
127 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
128 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
129 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
130 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
131 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
132 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
133 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
134 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
135 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
136 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
137 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
138 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
139 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
140 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
141 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
142 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
143 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
144 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
145 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
146 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
147 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
148 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
149 0xC2,
150};
151
152pub const leaf: [7584]u8 align(64) = .{
153 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
154 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
155 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
156 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
157 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
158 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
159 0xFF, 0xFF, 0x3F, 0x3F, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x3F, 0xFF, 0xAA, 0xFF, 0xFF, 0xFF, 0x3F,
160 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xDF, 0x5F, 0xDC, 0x1F, 0xCF, 0x0F, 0xFF, 0x1F, 0xDC, 0x1F,
161 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
162 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x20, 0x04, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF,
163 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
164 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
165 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
166 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
167 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
168 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
169 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
170 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0xA0, 0x04, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF,
171 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
172 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
173 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
174 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0xFF, 0xFF, 0x7F, 0xF8, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F,
175 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
176 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xC3, 0xFF, 0x03, 0x00, 0x1F, 0x50, 0x00, 0x00,
177 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xDF, 0xB8,
178 0x40, 0xD7, 0xFF, 0xFF, 0xFB, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xBF, 0xFF,
179 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
180 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xC3, 0xFF, 0x03, 0x00, 0x1F, 0x50, 0x00, 0x00,
181 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xDF, 0xB8,
182 0xC0, 0xD7, 0xFF, 0xFF, 0xFB, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xBF, 0xFF,
183 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
184 0x03, 0xFC, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
185 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFE, 0xFF, 0xFF, 0xFF, 0x7F, 0x02, 0xFF, 0xFF, 0xFF, 0xFF,
186 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x87, 0x07, 0x00,
187 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
188 0xFB, 0xFC, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
189 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFE, 0xFF, 0xFF, 0xFF, 0x7F, 0x02, 0xFF, 0xFF, 0xFF, 0xFF,
190 0xFF, 0x01, 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0xBF, 0xB6, 0x00, 0xFF, 0xFF, 0xFF, 0x87, 0x07, 0x00,
191 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x00, 0x00, 0xC0, 0xFE, 0xFF,
192 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x2F, 0x00, 0x60, 0xC0, 0x00, 0x9C,
193 0x00, 0x00, 0xFD, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0xE0, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
194 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x02, 0x00, 0x00, 0xFC, 0xFF, 0xFF, 0xFF, 0x07, 0x30, 0x04,
195 0x00, 0x00, 0xFF, 0x07, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xC3, 0xFF, 0xFF,
196 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xEF, 0x9F, 0xFF, 0xFD, 0xFF, 0x9F,
197 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xE7, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
198 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x24,
199 0xFF, 0xFF, 0x3F, 0x04, 0x10, 0x01, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x01, 0xFF, 0x07, 0xFF, 0xFF,
200 0xFF, 0x7E, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
201 0xF0, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x23, 0x00, 0x00, 0x01, 0xFF, 0x03, 0x00, 0xFE, 0xFF,
202 0xE1, 0x9F, 0xF9, 0xFF, 0xFF, 0xFD, 0xC5, 0x23, 0x00, 0x40, 0x00, 0xB0, 0x03, 0x00, 0x03, 0x10,
203 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x0F, 0xFF, 0x07, 0xFF, 0xFF,
204 0xFF, 0x7E, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFB, 0xFF, 0xFF, 0xFF,
205 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xCF, 0xFF, 0xFE, 0xFF,
206 0xEF, 0x9F, 0xF9, 0xFF, 0xFF, 0xFD, 0xC5, 0xF3, 0x9F, 0x79, 0x80, 0xB0, 0xCF, 0xFF, 0x03, 0x50,
207 0xE0, 0x87, 0xF9, 0xFF, 0xFF, 0xFD, 0x6D, 0x03, 0x00, 0x00, 0x00, 0x5E, 0x00, 0x00, 0x1C, 0x00,
208 0xE0, 0xBF, 0xFB, 0xFF, 0xFF, 0xFD, 0xED, 0x23, 0x00, 0x00, 0x01, 0x00, 0x03, 0x00, 0x00, 0x02,
209 0xE0, 0x9F, 0xF9, 0xFF, 0xFF, 0xFD, 0xED, 0x23, 0x00, 0x00, 0x00, 0xB0, 0x03, 0x00, 0x02, 0x00,
210 0xE8, 0xC7, 0x3D, 0xD6, 0x18, 0xC7, 0xFF, 0x03, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00,
211 0xEE, 0x87, 0xF9, 0xFF, 0xFF, 0xFD, 0x6D, 0xD3, 0x87, 0x39, 0x02, 0x5E, 0xC0, 0xFF, 0x3F, 0x00,
212 0xEE, 0xBF, 0xFB, 0xFF, 0xFF, 0xFD, 0xED, 0xF3, 0xBF, 0x3B, 0x01, 0x00, 0xCF, 0xFF, 0x00, 0xFE,
213 0xEE, 0x9F, 0xF9, 0xFF, 0xFF, 0xFD, 0xED, 0xF3, 0x9F, 0x39, 0xE0, 0xB0, 0xCF, 0xFF, 0x02, 0x00,
214 0xEC, 0xC7, 0x3D, 0xD6, 0x18, 0xC7, 0xFF, 0xC3, 0xC7, 0x3D, 0x81, 0x00, 0xC0, 0xFF, 0x00, 0x00,
215 0xE0, 0xDF, 0xFD, 0xFF, 0xFF, 0xFD, 0xFF, 0x23, 0x00, 0x00, 0x00, 0x27, 0x03, 0x00, 0x00, 0x00,
216 0xE1, 0xDF, 0xFD, 0xFF, 0xFF, 0xFD, 0xEF, 0x23, 0x00, 0x00, 0x00, 0x60, 0x03, 0x00, 0x06, 0x00,
217 0xF0, 0xDF, 0xFD, 0xFF, 0xFF, 0xFF, 0xFF, 0x27, 0x00, 0x40, 0x70, 0x80, 0x03, 0x00, 0x00, 0xFC,
218 0xE0, 0xFF, 0x7F, 0xFC, 0xFF, 0xFF, 0xFB, 0x2F, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
219 0xFF, 0xDF, 0xFD, 0xFF, 0xFF, 0xFD, 0xFF, 0xF3, 0xDF, 0x3D, 0x60, 0x27, 0xCF, 0xFF, 0x00, 0x00,
220 0xEF, 0xDF, 0xFD, 0xFF, 0xFF, 0xFD, 0xEF, 0xF3, 0xDF, 0x3D, 0x60, 0x60, 0xCF, 0xFF, 0x0E, 0x00,
221 0xFF, 0xDF, 0xFD, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xDF, 0x7D, 0xF0, 0x80, 0xCF, 0xFF, 0x00, 0xFC,
222 0xEE, 0xFF, 0x7F, 0xFC, 0xFF, 0xFF, 0xFB, 0x2F, 0x7F, 0x84, 0x5F, 0xFF, 0xC0, 0xFF, 0x0C, 0x00,
223 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x05, 0x00, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
224 0xD6, 0xF7, 0xFF, 0xFF, 0xAF, 0xFF, 0x05, 0x20, 0x5F, 0x00, 0x00, 0xF0, 0x00, 0x00, 0x00, 0x00,
225 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFE, 0xFF, 0xFF, 0xFF, 0x1F, 0x00, 0x00,
226 0x00, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
227 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0xFF, 0x7F, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00,
228 0xD6, 0xF7, 0xFF, 0xFF, 0xAF, 0xFF, 0xFF, 0x3F, 0x5F, 0x7F, 0xFF, 0xF3, 0x00, 0x00, 0x00, 0x00,
229 0x01, 0x00, 0x00, 0x03, 0xFF, 0x03, 0xA0, 0xC2, 0xFF, 0xFE, 0xFF, 0xFF, 0xFF, 0x1F, 0xFE, 0xFF,
230 0xDF, 0xFF, 0xFF, 0xFE, 0xFF, 0xFF, 0xFF, 0x1F, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
231 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x80, 0x00, 0x00, 0x3F, 0x3C, 0x62, 0xC0, 0xE1, 0xFF,
232 0x03, 0x40, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xBF, 0x20, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xF7,
233 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
234 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
235 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0xFF, 0xFF, 0x3F, 0x00, 0xFF, 0x00, 0x00, 0x00,
236 0xBF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFD, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
237 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
238 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF, 0xFF, 0xFF, 0xBF, 0x20, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xF7,
239 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
240 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
241 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
242 0xFF, 0xFF, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
243 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3D, 0x7F, 0x3D, 0xFF, 0xFF, 0xFF, 0xFF,
244 0xFF, 0x3D, 0xFF, 0xFF, 0xFF, 0xFF, 0x3D, 0x7F, 0x3D, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
245 0xFF, 0xFF, 0x3D, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x00, 0x00, 0x00,
246 0xFF, 0xFF, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x3F,
247 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3D, 0x7F, 0x3D, 0xFF, 0xFF, 0xFF, 0xFF,
248 0xFF, 0x3D, 0xFF, 0xFF, 0xFF, 0xFF, 0x3D, 0x7F, 0x3D, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
249 0xFF, 0xFF, 0x3D, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xE7, 0x00, 0xFE, 0x03, 0x00,
250 0xFF, 0xFF, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x3F,
251 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
252 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
253 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
254 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
255 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
256 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00,
257 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x9F, 0xFF, 0xFF,
258 0xFE, 0xFF, 0xFF, 0x07, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xC7, 0xFF, 0x01,
259 0xFF, 0xFF, 0x03, 0x80, 0xFF, 0xFF, 0x03, 0x00, 0xFF, 0xFF, 0x03, 0x00, 0xFF, 0xDF, 0x01, 0x00,
260 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0x00, 0x00, 0x80, 0x10, 0x00, 0x00, 0x00, 0x00,
261 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x9F, 0xFF, 0xFF,
262 0xFE, 0xFF, 0xFF, 0x07, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xC7, 0xFF, 0x01,
263 0xFF, 0xFF, 0x3F, 0x80, 0xFF, 0xFF, 0x1F, 0x00, 0xFF, 0xFF, 0x0F, 0x00, 0xFF, 0xDF, 0x0D, 0x00,
264 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x8F, 0x30, 0xFF, 0x03, 0x00, 0x00,
265 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01,
266 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x05, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00,
267 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x3F, 0x1F, 0x00,
268 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0xFF, 0xFF, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
269 0x00, 0xB8, 0xFF, 0x03, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01,
270 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00,
271 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0x0F, 0xFF, 0x0F, 0xC0, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x1F, 0x00,
272 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0xFF, 0xFF, 0xFF, 0x03, 0xFF, 0x07, 0x00, 0x00, 0x00, 0x00,
273 0xFF, 0xFF, 0x7F, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00,
274 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
275 0xE0, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0xE0, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
276 0xF8, 0xFF, 0xFF, 0xFF, 0x01, 0xC0, 0x00, 0xFC, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0x00,
277 0xFF, 0xFF, 0xFF, 0x0F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x9F,
278 0xFF, 0x03, 0xFF, 0x03, 0x80, 0x00, 0xFF, 0xBF, 0xFF, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
279 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0xFF, 0x03, 0x00, 0xF8, 0x0F, 0x00,
280 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00,
281 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0x00, 0x00, 0x00, 0xE0, 0x00, 0xFC, 0xFF, 0xFF, 0xFF, 0x3F,
282 0xFF, 0x01, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xE7, 0x00, 0x00, 0x00, 0x00, 0x00, 0xDE, 0x6F, 0x04,
283 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
284 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
285 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0xFF, 0xE3, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F,
286 0xFF, 0x01, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xE7, 0x00, 0x00, 0xF7, 0xFF, 0xFF, 0xFF, 0xFF, 0x07,
287 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
288 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
289 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x04, 0x00, 0x00, 0x00, 0x27, 0x00, 0xF0, 0x00, 0xFF, 0xFF,
290 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
291 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x80,
292 0x00, 0x00, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
293 0x84, 0xFC, 0x2F, 0x3F, 0x50, 0xFD, 0xFF, 0xF3, 0xE0, 0x43, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF,
294 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
295 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x01, 0x00, 0x10, 0x00, 0x00, 0x00, 0x02, 0x80,
296 0x00, 0x00, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0x1F, 0xE2, 0xFF, 0x01, 0x00,
297 0x84, 0xFC, 0x2F, 0x3F, 0x50, 0xFD, 0xFF, 0xF3, 0xE0, 0x43, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF,
298 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
299 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
300 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0x78, 0x0C, 0x00,
301 0xFF, 0xFF, 0xFF, 0xFF, 0xBF, 0x20, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x80, 0x00, 0x00,
302 0xFF, 0xFF, 0x7F, 0x00, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0x00, 0x00, 0x00, 0x00,
303 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
304 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0xF8, 0x0F, 0x00,
305 0xFF, 0xFF, 0xFF, 0xFF, 0xBF, 0x20, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x80, 0x00, 0x80,
306 0xFF, 0xFF, 0x7F, 0x00, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0xFF, 0xFF, 0xFF, 0xFF,
307 0xE0, 0x00, 0x00, 0x00, 0xFE, 0x03, 0x3E, 0x1F, 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
308 0xFF, 0xFF, 0x7F, 0xE0, 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xF7,
309 0xE0, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
310 0xFF, 0x7F, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF,
311 0xE0, 0x00, 0x00, 0x00, 0xFE, 0xFF, 0x3E, 0x1F, 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
312 0xFF, 0xFF, 0x7F, 0xE6, 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
313 0xE0, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
314 0xFF, 0x7F, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF,
315 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
316 0xFF, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F,
317 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
318 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
319 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
320 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
321 0xFF, 0x1F, 0xFF, 0xFF, 0x00, 0x0C, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x80,
322 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00,
323 0x00, 0x00, 0x80, 0xFF, 0xFC, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
324 0xFF, 0xF9, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0xEB, 0x03, 0x00, 0x00, 0xFC, 0xFF,
325 0xFF, 0x1F, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xF0, 0xBF,
326 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x00,
327 0x00, 0x00, 0x80, 0xFF, 0xFC, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
328 0xFF, 0xF9, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0xEB, 0x03, 0x00, 0x00, 0xFC, 0xFF,
329 0xBB, 0xF7, 0xFF, 0xFF, 0x07, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00,
330 0xFC, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0x68,
331 0x00, 0xFC, 0xFF, 0xFF, 0x3F, 0x00, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x1F,
332 0xF0, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x00, 0x80, 0x00, 0x00, 0xDF, 0xFF, 0x00, 0x7C,
333 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x10, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00,
334 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0xFF, 0x03, 0xFF, 0xFF, 0xFF, 0xE8,
335 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0xFF, 0xFF, 0xFF, 0x1F,
336 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x80, 0xFF, 0x03, 0xFF, 0xFF, 0xFF, 0x7F,
337 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x00, 0x00, 0xF7, 0x0F, 0x00, 0x00, 0xFF, 0xFF, 0x7F, 0xC4,
338 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x62, 0x3E, 0x05, 0x00, 0x00, 0x38, 0xFF, 0x07, 0x1C, 0x00,
339 0x7E, 0x7E, 0x7E, 0x00, 0x7F, 0x7F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xF7, 0xFF, 0x03, 0xFF, 0xFF,
340 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x00, 0x00,
341 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0xFF, 0x3F, 0xFF, 0x03, 0xFF, 0xFF, 0x7F, 0xFC,
342 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x00, 0x38, 0xFF, 0xFF, 0x7C, 0x00,
343 0x7E, 0x7E, 0x7E, 0x00, 0x7F, 0x7F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xF7, 0xFF, 0x03, 0xFF, 0xFF,
344 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x37, 0xFF, 0x03,
345 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF,
346 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00,
347 0x7F, 0x00, 0xF8, 0xA0, 0xFF, 0xFD, 0x7F, 0x5F, 0xDB, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
348 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x00, 0x00, 0x00, 0xF8, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
349 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF,
350 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00,
351 0x7F, 0x00, 0xF8, 0xE0, 0xFF, 0xFD, 0x7F, 0x5F, 0xDB, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
352 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x00, 0x00, 0x00, 0xF8, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
353 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0xF0, 0xFF, 0xFF, 0xFF,
354 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
355 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
356 0xFF, 0xFF, 0xFC, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0x03,
357 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x8A, 0xAA,
358 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F,
359 0x00, 0x00, 0x00, 0x00, 0xFE, 0xFF, 0xFF, 0x07, 0xFE, 0xFF, 0xFF, 0x07, 0xC0, 0xFF, 0xFF, 0xFF,
360 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF, 0xFF, 0x7F, 0xFC, 0xFC, 0xFC, 0x1C, 0x00, 0x00, 0x00, 0x00,
361 0xFF, 0xFF, 0x00, 0x00, 0xFF, 0xFF, 0x18, 0x00, 0x00, 0xE0, 0x00, 0x00, 0x00, 0x00, 0x8A, 0xAA,
362 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F,
363 0x00, 0x00, 0xFF, 0x03, 0xFE, 0xFF, 0xFF, 0x87, 0xFE, 0xFF, 0xFF, 0x07, 0xE0, 0xFF, 0xFF, 0xFF,
364 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0xFC, 0xFC, 0xFC, 0x1C, 0x00, 0x00, 0x00, 0x00,
365 0xFF, 0xEF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xB7, 0xFF, 0x3F, 0xFF, 0x3F, 0x00, 0x00, 0x00, 0x00,
366 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07,
367 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0x00,
368 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
369 0xFF, 0xEF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xB7, 0xFF, 0x3F, 0xFF, 0x3F, 0x00, 0x00, 0x00, 0x00,
370 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07,
371 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0x00,
372 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20,
373 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
374 0xFF, 0xFF, 0xFF, 0x1F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00,
375 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0xE0, 0xFF, 0xFF, 0xFF, 0x07, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00,
376 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0xFF, 0x3E, 0x00, 0x00, 0x00, 0x00, 0x00,
377 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
378 0xFF, 0xFF, 0xFF, 0x1F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x00, 0x01, 0x00, 0x00, 0x00,
379 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0xE0, 0xFF, 0xFF, 0xFF, 0x07, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07,
380 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0xFF, 0x3E, 0x00, 0x00, 0x00, 0x00, 0x00,
381 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
382 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F,
383 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0xFF, 0xF7,
384 0xFF, 0xF7, 0xB7, 0xFF, 0xFB, 0xFF, 0xFB, 0x1B, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
385 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
386 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0x03, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F,
387 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0xFF, 0xF7,
388 0xFF, 0xF7, 0xB7, 0xFF, 0xFB, 0xFF, 0xFB, 0x1B, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
389 0x3F, 0xFD, 0xFF, 0xFF, 0xFF, 0xFF, 0xBF, 0x91, 0xFF, 0xFF, 0x3F, 0x00, 0xFF, 0xFF, 0x7F, 0x00,
390 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x37, 0x00,
391 0xFF, 0xFF, 0x3F, 0x00, 0xFF, 0xFF, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
392 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xC0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
393 0x01, 0x00, 0xEF, 0xFE, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x1F,
394 0xFF, 0xFF, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFE, 0xFF, 0xFF, 0x1F, 0x00, 0x00, 0x00,
395 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0xFF, 0xFF, 0x3F, 0x00, 0xFF, 0xFF, 0x07, 0x00,
396 0xFF, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
397 0x6F, 0xF0, 0xEF, 0xFE, 0xFF, 0xFF, 0x3F, 0x87, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x1F,
398 0xFF, 0xFF, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFE, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x00,
399 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0xFF, 0xFF, 0x3F, 0x00, 0xFF, 0xFF, 0x07, 0x00,
400 0xFF, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
401 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
402 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00,
403 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
404 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
405 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
406 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00,
407 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
408 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
409 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
410 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
411 0xFF, 0xFF, 0xFF, 0x1F, 0x80, 0x00, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF,
412 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x7F, 0x00,
413 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
414 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1B, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE0,
415 0xFF, 0xFF, 0xFF, 0x1F, 0x80, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x00, 0x00, 0x00, 0xFF, 0xFF,
416 0x3F, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x7F, 0x00,
417 0xF8, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x26, 0x00,
418 0xF8, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x01, 0x00, 0x00,
419 0xF8, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x00, 0x90, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x47, 0x00,
420 0xF8, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x1E, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x00,
421 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x00, 0xC0, 0xFF, 0x3F, 0x80,
422 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x04, 0x00, 0xFF, 0xFF, 0xFF, 0x01, 0xFF, 0x03,
423 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xDF, 0xFF, 0xF0, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x4F, 0x00,
424 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0xDE, 0xFF, 0x17, 0x00, 0x00, 0x00, 0x00,
425 0xFF, 0xFF, 0xFB, 0xFF, 0xFF, 0x0F, 0x00, 0x80, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
426 0x7F, 0xBD, 0xFF, 0xBF, 0xFF, 0x01, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x00, 0x00,
427 0xE0, 0x9F, 0xF9, 0xFF, 0xFF, 0xFD, 0xED, 0x23, 0x00, 0x00, 0x01, 0xE0, 0x03, 0x00, 0x00, 0x00,
428 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
429 0xFF, 0xFF, 0xFB, 0xFF, 0xFF, 0xFF, 0xFF, 0xC0, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
430 0x7F, 0xBD, 0xFF, 0xBF, 0xFF, 0x01, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0xFF, 0x03,
431 0xEF, 0x9F, 0xF9, 0xFF, 0xFF, 0xFD, 0xED, 0xFB, 0x9F, 0x39, 0x81, 0xE0, 0xCF, 0x1F, 0x1F, 0x00,
432 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
433 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0x00, 0x80, 0x07, 0x00, 0x80, 0x03, 0x00, 0x00, 0x00,
434 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0xB0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
435 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
436 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0x00,
437 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0xFF, 0xC3, 0x03, 0x00, 0x00, 0x00,
438 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xBF, 0x00, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00,
439 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
440 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0x01, 0x00, 0x00, 0x3F, 0x00, 0x00, 0x00, 0x00,
441 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
442 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
443 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x00, 0x00, 0x00, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
444 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
445 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x11, 0x00, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00,
446 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
447 0xFF, 0xFF, 0xFF, 0xE7, 0xFF, 0x0F, 0xFF, 0x03, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
448 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
449 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
450 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x80,
451 0x7F, 0xF2, 0x6F, 0xFF, 0xFF, 0xFF, 0x00, 0x80, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
452 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFC, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x00, 0x0A, 0x00, 0x00, 0x00,
453 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
454 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x00, 0x80,
455 0x7F, 0xF2, 0x6F, 0xFF, 0xFF, 0xFF, 0xBF, 0xF9, 0x0F, 0x00, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00,
456 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFC, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFC, 0x1B, 0x00, 0x00, 0x00,
457 0x01, 0xF8, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x04, 0x00, 0x00, 0x01, 0xF0, 0xFF, 0xFF, 0xFF, 0xFF,
458 0xFF, 0x03, 0x00, 0x20, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01,
459 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
460 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
461 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
462 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x00,
463 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0x80, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
464 0xFF, 0xFF, 0xFF, 0x23, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01,
465 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
466 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
467 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
468 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xEF, 0x6F,
469 0xFF, 0xFD, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF,
470 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
471 0x7F, 0xFB, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x00, 0x40, 0x00, 0x00, 0x00, 0xBF, 0xFD, 0xFF, 0xFF,
472 0xFF, 0x03, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
473 0xFF, 0xFD, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0x01, 0x00, 0xFF, 0x03, 0x00, 0x00, 0xFC, 0xFF,
474 0xFF, 0xFF, 0xFC, 0xFF, 0xFF, 0xFE, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
475 0x7F, 0xFB, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0xB4, 0xFF, 0x00, 0xFF, 0x03, 0xBF, 0xFD, 0xFF, 0xFF,
476 0xFF, 0x7F, 0xFB, 0x01, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
477 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
478 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x07, 0x00,
479 0xF4, 0xFF, 0xFD, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
480 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
481 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
482 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x7F, 0x00,
483 0xFF, 0xFF, 0xFD, 0xFF, 0xFF, 0xFF, 0xFF, 0xC7, 0x07, 0x00, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00,
484 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
485 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00,
486 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
487 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
488 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
489 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x7E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
490 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
491 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
492 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
493 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
494 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
495 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0x00, 0x00, 0x00,
496 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
497 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
498 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
499 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE0, 0xE3, 0x07, 0xF8,
500 0xE7, 0x0F, 0x00, 0x00, 0x00, 0x3C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
501 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
502 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
503 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
504 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
505 0xFF, 0xFF, 0xFF, 0x7F, 0xE0, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
506 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
507 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0xFF, 0xFF,
508 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x00,
509 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xF8, 0xFF, 0xFF, 0xE0,
510 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
511 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0x03, 0xFF, 0xFF,
512 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0x03, 0xFF, 0xFF, 0xFF, 0x3F, 0x1F, 0x00,
513 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x0F, 0x00, 0xFF, 0x03, 0xF8, 0xFF, 0xFF, 0xE0,
514 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
515 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
516 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
517 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00,
518 0x00, 0x00, 0xF8, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0B, 0x00, 0x00, 0x00,
519 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
520 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
521 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x87, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
522 0xFF, 0x80, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1B, 0x00, 0x03, 0x00,
523 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
524 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0x00, 0x00, 0x00,
525 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
526 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
527 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
528 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F,
529 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
530 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
531 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
532 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x7F, 0x6F, 0xFF, 0x7F,
533 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0xFF, 0x1F,
534 0xFF, 0x01, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
535 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
536 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
537 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
538 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0x03,
539 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0xFF, 0x1F,
540 0xFF, 0x01, 0xFF, 0x63, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
541 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
542 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
543 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
544 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00,
545 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
546 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
547 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
548 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
549 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xDF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
550 0xFF, 0xFF, 0xFF, 0xDF, 0x64, 0xDE, 0xFF, 0xEB, 0xEF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
551 0xBF, 0xE7, 0xDF, 0xDF, 0xFF, 0xFF, 0xFF, 0x7B, 0x5F, 0xFC, 0xFD, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
552 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
553 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
554 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF, 0xFF, 0xFD, 0xFF, 0xFF, 0xF7, 0xFF, 0xFF, 0xFF, 0xF7,
555 0xFF, 0xFF, 0xDF, 0xFF, 0xFF, 0xFF, 0xDF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF,
556 0xFF, 0xFD, 0xFF, 0xFF, 0xFF, 0xFD, 0xFF, 0xFF, 0xF7, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
557 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
558 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF, 0xFF, 0xFD, 0xFF, 0xFF, 0xF7, 0xFF, 0xFF, 0xFF, 0xF7,
559 0xFF, 0xFF, 0xDF, 0xFF, 0xFF, 0xFF, 0xDF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF,
560 0xFF, 0xFD, 0xFF, 0xFF, 0xFF, 0xFD, 0xFF, 0xFF, 0xF7, 0xCF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
561 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F, 0xF8, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0x20, 0x00,
562 0x10, 0x00, 0x00, 0xF8, 0xFE, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
563 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
564 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
565 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x00,
566 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
567 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0x80, 0x3F, 0x00, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
568 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
569 0x7F, 0xFF, 0xFF, 0xF9, 0xDB, 0x07, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x00,
570 0x00, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
571 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0xFF, 0x3F, 0xFF, 0x43, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
572 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
573 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
574 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0x00,
575 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
576 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
577 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
578 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x7F, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03,
579 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
580 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
581 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
582 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x0F, 0x00, 0x00,
583 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
584 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
585 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
586 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x03,
587 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
588 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
589 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
590 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
591 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
592 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
593 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
594 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x1F, 0x00, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00,
595 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F, 0xFF, 0x03, 0x00, 0x00, 0x00, 0x00,
596 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
597 0xEF, 0xFF, 0xFF, 0xFF, 0x96, 0xFE, 0xF7, 0x0A, 0x84, 0xEA, 0x96, 0xAA, 0x96, 0xF7, 0xF7, 0x5E,
598 0xFF, 0xFB, 0xFF, 0x0F, 0xEE, 0xFB, 0xFF, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
599 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
600 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
601 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
602 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
603 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
604 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
605 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
606 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x00, 0xFF, 0xFF,
607 0xFF, 0xFF, 0xFF, 0x3F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
608 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
609 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
610 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
611 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x07, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
612 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
613 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
614 0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
615 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
616 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
617 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
618 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
619 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0x00, 0x00,
620 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
621 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
622 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
623 0xFF, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
624 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
625 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
626 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
627};
lib/compiler/aro/aro/features.zig deleted-76
...@@ -1,76 +0,0 @@
1const std = @import("std");
2const Compilation = @import("Compilation.zig");
3const target_util = @import("target.zig");
4
5/// Used to implement the __has_feature macro.
6pub fn hasFeature(comp: *Compilation, ext: []const u8) bool {
7 const list = .{
8 .assume_nonnull = true,
9 .attribute_analyzer_noreturn = true,
10 .attribute_availability = true,
11 .attribute_availability_with_message = true,
12 .attribute_availability_app_extension = true,
13 .attribute_availability_with_version_underscores = true,
14 .attribute_availability_tvos = true,
15 .attribute_availability_watchos = true,
16 .attribute_availability_with_strict = true,
17 .attribute_availability_with_replacement = true,
18 .attribute_availability_in_templates = true,
19 .attribute_availability_swift = true,
20 .attribute_cf_returns_not_retained = true,
21 .attribute_cf_returns_retained = true,
22 .attribute_cf_returns_on_parameters = true,
23 .attribute_deprecated_with_message = true,
24 .attribute_deprecated_with_replacement = true,
25 .attribute_ext_vector_type = true,
26 .attribute_ns_returns_not_retained = true,
27 .attribute_ns_returns_retained = true,
28 .attribute_ns_consumes_self = true,
29 .attribute_ns_consumed = true,
30 .attribute_cf_consumed = true,
31 .attribute_overloadable = true,
32 .attribute_unavailable_with_message = true,
33 .attribute_unused_on_fields = true,
34 .attribute_diagnose_if_objc = true,
35 .blocks = false, // TODO
36 .c_thread_safety_attributes = true,
37 .enumerator_attributes = true,
38 .nullability = true,
39 .nullability_on_arrays = true,
40 .nullability_nullable_result = true,
41 .c_alignas = comp.langopts.standard.atLeast(.c11),
42 .c_alignof = comp.langopts.standard.atLeast(.c11),
43 .c_atomic = comp.langopts.standard.atLeast(.c11),
44 .c_generic_selections = comp.langopts.standard.atLeast(.c11),
45 .c_static_assert = comp.langopts.standard.atLeast(.c11),
46 .c_thread_local = comp.langopts.standard.atLeast(.c11) and target_util.isTlsSupported(comp.target),
47 };
48 inline for (@typeInfo(@TypeOf(list)).@"struct".fields) |f| {
49 if (std.mem.eql(u8, f.name, ext)) return @field(list, f.name);
50 }
51 return false;
52}
53
54/// Used to implement the __has_extension macro.
55pub fn hasExtension(comp: *Compilation, ext: []const u8) bool {
56 const list = .{
57 // C11 features
58 .c_alignas = true,
59 .c_alignof = true,
60 .c_atomic = false, // TODO
61 .c_generic_selections = true,
62 .c_static_assert = true,
63 .c_thread_local = target_util.isTlsSupported(comp.target),
64 // misc
65 .overloadable_unmarked = false, // TODO
66 .statement_attributes_with_gnu_syntax = false, // TODO
67 .gnu_asm = true,
68 .gnu_asm_goto_with_outputs = true,
69 .matrix_types = false, // TODO
70 .matrix_types_scalar_division = false, // TODO
71 };
72 inline for (@typeInfo(@TypeOf(list)).@"struct".fields) |f| {
73 if (std.mem.eql(u8, f.name, ext)) return @field(list, f.name);
74 }
75 return false;
76}
lib/compiler/aro/aro/pragmas/gcc.zig deleted-199
...@@ -1,199 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const Compilation = @import("../Compilation.zig");
4const Pragma = @import("../Pragma.zig");
5const Diagnostics = @import("../Diagnostics.zig");
6const Preprocessor = @import("../Preprocessor.zig");
7const Parser = @import("../Parser.zig");
8const TokenIndex = @import("../Tree.zig").TokenIndex;
9
10const GCC = @This();
11
12pragma: Pragma = .{
13 .beforeParse = beforeParse,
14 .beforePreprocess = beforePreprocess,
15 .afterParse = afterParse,
16 .deinit = deinit,
17 .preprocessorHandler = preprocessorHandler,
18 .parserHandler = parserHandler,
19 .preserveTokens = preserveTokens,
20},
21original_options: Diagnostics.Options = .{},
22options_stack: std.ArrayListUnmanaged(Diagnostics.Options) = .empty,
23
24const Directive = enum {
25 warning,
26 @"error",
27 diagnostic,
28 poison,
29 const Diagnostics = enum {
30 ignored,
31 warning,
32 @"error",
33 fatal,
34 push,
35 pop,
36 };
37};
38
39fn beforePreprocess(pragma: *Pragma, comp: *Compilation) void {
40 var self: *GCC = @fieldParentPtr("pragma", pragma);
41 self.original_options = comp.diagnostics.options;
42}
43
44fn beforeParse(pragma: *Pragma, comp: *Compilation) void {
45 var self: *GCC = @fieldParentPtr("pragma", pragma);
46 comp.diagnostics.options = self.original_options;
47 self.options_stack.items.len = 0;
48}
49
50fn afterParse(pragma: *Pragma, comp: *Compilation) void {
51 var self: *GCC = @fieldParentPtr("pragma", pragma);
52 comp.diagnostics.options = self.original_options;
53 self.options_stack.items.len = 0;
54}
55
56pub fn init(allocator: mem.Allocator) !*Pragma {
57 var gcc = try allocator.create(GCC);
58 gcc.* = .{};
59 return &gcc.pragma;
60}
61
62fn deinit(pragma: *Pragma, comp: *Compilation) void {
63 var self: *GCC = @fieldParentPtr("pragma", pragma);
64 self.options_stack.deinit(comp.gpa);
65 comp.gpa.destroy(self);
66}
67
68fn diagnosticHandler(self: *GCC, pp: *Preprocessor, start_idx: TokenIndex) Pragma.Error!void {
69 const diagnostic_tok = pp.tokens.get(start_idx);
70 if (diagnostic_tok.id == .nl) return;
71
72 const diagnostic = std.meta.stringToEnum(Directive.Diagnostics, pp.expandedSlice(diagnostic_tok)) orelse
73 return error.UnknownPragma;
74
75 switch (diagnostic) {
76 .ignored, .warning, .@"error", .fatal => {
77 const str = Pragma.pasteTokens(pp, start_idx + 1) catch |err| switch (err) {
78 error.ExpectedStringLiteral => {
79 return pp.comp.addDiagnostic(.{
80 .tag = .pragma_requires_string_literal,
81 .loc = diagnostic_tok.loc,
82 .extra = .{ .str = "GCC diagnostic" },
83 }, pp.expansionSlice(start_idx));
84 },
85 else => |e| return e,
86 };
87 if (!mem.startsWith(u8, str, "-W")) {
88 const next = pp.tokens.get(start_idx + 1);
89 return pp.comp.addDiagnostic(.{
90 .tag = .malformed_warning_check,
91 .loc = next.loc,
92 .extra = .{ .str = "GCC diagnostic" },
93 }, pp.expansionSlice(start_idx + 1));
94 }
95 const new_kind: Diagnostics.Kind = switch (diagnostic) {
96 .ignored => .off,
97 .warning => .warning,
98 .@"error" => .@"error",
99 .fatal => .@"fatal error",
100 else => unreachable,
101 };
102
103 try pp.comp.diagnostics.set(str[2..], new_kind);
104 },
105 .push => try self.options_stack.append(pp.comp.gpa, pp.comp.diagnostics.options),
106 .pop => pp.comp.diagnostics.options = self.options_stack.popOrNull() orelse self.original_options,
107 }
108}
109
110fn preprocessorHandler(pragma: *Pragma, pp: *Preprocessor, start_idx: TokenIndex) Pragma.Error!void {
111 var self: *GCC = @fieldParentPtr("pragma", pragma);
112 const directive_tok = pp.tokens.get(start_idx + 1);
113 if (directive_tok.id == .nl) return;
114
115 const gcc_pragma = std.meta.stringToEnum(Directive, pp.expandedSlice(directive_tok)) orelse
116 return pp.comp.addDiagnostic(.{
117 .tag = .unknown_gcc_pragma,
118 .loc = directive_tok.loc,
119 }, pp.expansionSlice(start_idx + 1));
120
121 switch (gcc_pragma) {
122 .warning, .@"error" => {
123 const text = Pragma.pasteTokens(pp, start_idx + 2) catch |err| switch (err) {
124 error.ExpectedStringLiteral => {
125 return pp.comp.addDiagnostic(.{
126 .tag = .pragma_requires_string_literal,
127 .loc = directive_tok.loc,
128 .extra = .{ .str = @tagName(gcc_pragma) },
129 }, pp.expansionSlice(start_idx + 1));
130 },
131 else => |e| return e,
132 };
133 const extra = Diagnostics.Message.Extra{ .str = try pp.comp.diagnostics.arena.allocator().dupe(u8, text) };
134 const diagnostic_tag: Diagnostics.Tag = if (gcc_pragma == .warning) .pragma_warning_message else .pragma_error_message;
135 return pp.comp.addDiagnostic(
136 .{ .tag = diagnostic_tag, .loc = directive_tok.loc, .extra = extra },
137 pp.expansionSlice(start_idx + 1),
138 );
139 },
140 .diagnostic => return self.diagnosticHandler(pp, start_idx + 2) catch |err| switch (err) {
141 error.UnknownPragma => {
142 const tok = pp.tokens.get(start_idx + 2);
143 return pp.comp.addDiagnostic(.{
144 .tag = .unknown_gcc_pragma_directive,
145 .loc = tok.loc,
146 }, pp.expansionSlice(start_idx + 2));
147 },
148 else => |e| return e,
149 },
150 .poison => {
151 var i: u32 = 2;
152 while (true) : (i += 1) {
153 const tok = pp.tokens.get(start_idx + i);
154 if (tok.id == .nl) break;
155
156 if (!tok.id.isMacroIdentifier()) {
157 return pp.comp.addDiagnostic(.{
158 .tag = .pragma_poison_identifier,
159 .loc = tok.loc,
160 }, pp.expansionSlice(start_idx + i));
161 }
162 const str = pp.expandedSlice(tok);
163 if (pp.defines.get(str) != null) {
164 try pp.comp.addDiagnostic(.{
165 .tag = .pragma_poison_macro,
166 .loc = tok.loc,
167 }, pp.expansionSlice(start_idx + i));
168 }
169 try pp.poisoned_identifiers.put(str, {});
170 }
171 return;
172 },
173 }
174}
175
176fn parserHandler(pragma: *Pragma, p: *Parser, start_idx: TokenIndex) Compilation.Error!void {
177 var self: *GCC = @fieldParentPtr("pragma", pragma);
178 const directive_tok = p.pp.tokens.get(start_idx + 1);
179 if (directive_tok.id == .nl) return;
180 const name = p.pp.expandedSlice(directive_tok);
181 if (mem.eql(u8, name, "diagnostic")) {
182 return self.diagnosticHandler(p.pp, start_idx + 2) catch |err| switch (err) {
183 error.UnknownPragma => {}, // handled during preprocessing
184 error.StopPreprocessing => unreachable, // Only used by #pragma once
185 else => |e| return e,
186 };
187 }
188}
189
190fn preserveTokens(_: *Pragma, pp: *Preprocessor, start_idx: TokenIndex) bool {
191 const next = pp.tokens.get(start_idx + 1);
192 if (next.id != .nl) {
193 const name = pp.expandedSlice(next);
194 if (mem.eql(u8, name, "poison")) {
195 return false;
196 }
197 }
198 return true;
199}
lib/compiler/aro/aro/pragmas/message.zig deleted-50
...@@ -1,50 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const Compilation = @import("../Compilation.zig");
4const Pragma = @import("../Pragma.zig");
5const Diagnostics = @import("../Diagnostics.zig");
6const Preprocessor = @import("../Preprocessor.zig");
7const Parser = @import("../Parser.zig");
8const TokenIndex = @import("../Tree.zig").TokenIndex;
9const Source = @import("../Source.zig");
10
11const Message = @This();
12
13pragma: Pragma = .{
14 .deinit = deinit,
15 .preprocessorHandler = preprocessorHandler,
16},
17
18pub fn init(allocator: mem.Allocator) !*Pragma {
19 var once = try allocator.create(Message);
20 once.* = .{};
21 return &once.pragma;
22}
23
24fn deinit(pragma: *Pragma, comp: *Compilation) void {
25 const self: *Message = @fieldParentPtr("pragma", pragma);
26 comp.gpa.destroy(self);
27}
28
29fn preprocessorHandler(_: *Pragma, pp: *Preprocessor, start_idx: TokenIndex) Pragma.Error!void {
30 const message_tok = pp.tokens.get(start_idx);
31 const message_expansion_locs = pp.expansionSlice(start_idx);
32
33 const str = Pragma.pasteTokens(pp, start_idx + 1) catch |err| switch (err) {
34 error.ExpectedStringLiteral => {
35 return pp.comp.addDiagnostic(.{
36 .tag = .pragma_requires_string_literal,
37 .loc = message_tok.loc,
38 .extra = .{ .str = "message" },
39 }, message_expansion_locs);
40 },
41 else => |e| return e,
42 };
43
44 const loc = if (message_expansion_locs.len != 0)
45 message_expansion_locs[message_expansion_locs.len - 1]
46 else
47 message_tok.loc;
48 const extra = Diagnostics.Message.Extra{ .str = try pp.comp.diagnostics.arena.allocator().dupe(u8, str) };
49 return pp.comp.addDiagnostic(.{ .tag = .pragma_message, .loc = loc, .extra = extra }, &.{});
50}
lib/compiler/aro/aro/pragmas/once.zig deleted-56
...@@ -1,56 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const Compilation = @import("../Compilation.zig");
4const Pragma = @import("../Pragma.zig");
5const Diagnostics = @import("../Diagnostics.zig");
6const Preprocessor = @import("../Preprocessor.zig");
7const Parser = @import("../Parser.zig");
8const TokenIndex = @import("../Tree.zig").TokenIndex;
9const Source = @import("../Source.zig");
10
11const Once = @This();
12
13pragma: Pragma = .{
14 .afterParse = afterParse,
15 .deinit = deinit,
16 .preprocessorHandler = preprocessorHandler,
17},
18pragma_once: std.AutoHashMap(Source.Id, void),
19preprocess_count: u32 = 0,
20
21pub fn init(allocator: mem.Allocator) !*Pragma {
22 var once = try allocator.create(Once);
23 once.* = .{
24 .pragma_once = std.AutoHashMap(Source.Id, void).init(allocator),
25 };
26 return &once.pragma;
27}
28
29fn afterParse(pragma: *Pragma, _: *Compilation) void {
30 var self: *Once = @fieldParentPtr("pragma", pragma);
31 self.pragma_once.clearRetainingCapacity();
32}
33
34fn deinit(pragma: *Pragma, comp: *Compilation) void {
35 var self: *Once = @fieldParentPtr("pragma", pragma);
36 self.pragma_once.deinit();
37 comp.gpa.destroy(self);
38}
39
40fn preprocessorHandler(pragma: *Pragma, pp: *Preprocessor, start_idx: TokenIndex) Pragma.Error!void {
41 var self: *Once = @fieldParentPtr("pragma", pragma);
42 const name_tok = pp.tokens.get(start_idx);
43 const next = pp.tokens.get(start_idx + 1);
44 if (next.id != .nl) {
45 try pp.comp.addDiagnostic(.{
46 .tag = .extra_tokens_directive_end,
47 .loc = name_tok.loc,
48 }, pp.expansionSlice(start_idx + 1));
49 }
50 const seen = self.preprocess_count == pp.preprocess_count;
51 const prev = try self.pragma_once.fetchPut(name_tok.loc.id, {});
52 if (prev != null and !seen) {
53 return error.StopPreprocessing;
54 }
55 self.preprocess_count = pp.preprocess_count;
56}
lib/compiler/aro/aro/pragmas/pack.zig deleted-164
...@@ -1,164 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const Compilation = @import("../Compilation.zig");
4const Pragma = @import("../Pragma.zig");
5const Diagnostics = @import("../Diagnostics.zig");
6const Preprocessor = @import("../Preprocessor.zig");
7const Parser = @import("../Parser.zig");
8const Tree = @import("../Tree.zig");
9const TokenIndex = Tree.TokenIndex;
10
11const Pack = @This();
12
13pragma: Pragma = .{
14 .deinit = deinit,
15 .parserHandler = parserHandler,
16 .preserveTokens = preserveTokens,
17},
18stack: std.ArrayListUnmanaged(struct { label: []const u8, val: u8 }) = .empty,
19
20pub fn init(allocator: mem.Allocator) !*Pragma {
21 var pack = try allocator.create(Pack);
22 pack.* = .{};
23 return &pack.pragma;
24}
25
26fn deinit(pragma: *Pragma, comp: *Compilation) void {
27 var self: *Pack = @fieldParentPtr("pragma", pragma);
28 self.stack.deinit(comp.gpa);
29 comp.gpa.destroy(self);
30}
31
32fn parserHandler(pragma: *Pragma, p: *Parser, start_idx: TokenIndex) Compilation.Error!void {
33 var pack: *Pack = @fieldParentPtr("pragma", pragma);
34 var idx = start_idx + 1;
35 const l_paren = p.pp.tokens.get(idx);
36 if (l_paren.id != .l_paren) {
37 return p.comp.addDiagnostic(.{
38 .tag = .pragma_pack_lparen,
39 .loc = l_paren.loc,
40 }, p.pp.expansionSlice(idx));
41 }
42 idx += 1;
43
44 // TODO -fapple-pragma-pack -fxl-pragma-pack
45 const apple_or_xl = false;
46 const tok_ids = p.pp.tokens.items(.id);
47 const arg = idx;
48 switch (tok_ids[arg]) {
49 .identifier => {
50 idx += 1;
51 const Action = enum {
52 show,
53 push,
54 pop,
55 };
56 const action = std.meta.stringToEnum(Action, p.tokSlice(arg)) orelse {
57 return p.errTok(.pragma_pack_unknown_action, arg);
58 };
59 switch (action) {
60 .show => {
61 try p.errExtra(.pragma_pack_show, arg, .{ .unsigned = p.pragma_pack orelse 8 });
62 },
63 .push, .pop => {
64 var new_val: ?u8 = null;
65 var label: ?[]const u8 = null;
66 if (tok_ids[idx] == .comma) {
67 idx += 1;
68 const next = idx;
69 idx += 1;
70 switch (tok_ids[next]) {
71 .pp_num => new_val = (try packInt(p, next)) orelse return,
72 .identifier => {
73 label = p.tokSlice(next);
74 if (tok_ids[idx] == .comma) {
75 idx += 1;
76 const int = idx;
77 idx += 1;
78 if (tok_ids[int] != .pp_num) return p.errTok(.pragma_pack_int_ident, int);
79 new_val = (try packInt(p, int)) orelse return;
80 }
81 },
82 else => return p.errTok(.pragma_pack_int_ident, next),
83 }
84 }
85 if (action == .push) {
86 try pack.stack.append(p.gpa, .{ .label = label orelse "", .val = p.pragma_pack orelse 8 });
87 } else {
88 pack.pop(p, label);
89 if (new_val != null) {
90 try p.errTok(.pragma_pack_undefined_pop, arg);
91 } else if (pack.stack.items.len == 0) {
92 try p.errTok(.pragma_pack_empty_stack, arg);
93 }
94 }
95 if (new_val) |some| {
96 p.pragma_pack = some;
97 }
98 },
99 }
100 },
101 .r_paren => if (apple_or_xl) {
102 pack.pop(p, null);
103 } else {
104 p.pragma_pack = null;
105 },
106 .pp_num => {
107 const new_val = (try packInt(p, arg)) orelse return;
108 idx += 1;
109 if (apple_or_xl) {
110 try pack.stack.append(p.gpa, .{ .label = "", .val = p.pragma_pack });
111 }
112 p.pragma_pack = new_val;
113 },
114 else => {},
115 }
116
117 if (tok_ids[idx] != .r_paren) {
118 return p.errTok(.pragma_pack_rparen, idx);
119 }
120}
121
122fn packInt(p: *Parser, tok_i: TokenIndex) Compilation.Error!?u8 {
123 const res = p.parseNumberToken(tok_i) catch |err| switch (err) {
124 error.ParsingFailed => {
125 try p.errTok(.pragma_pack_int, tok_i);
126 return null;
127 },
128 else => |e| return e,
129 };
130 const int = res.val.toInt(u64, p.comp) orelse 99;
131 switch (int) {
132 1, 2, 4, 8, 16 => return @intCast(int),
133 else => {
134 try p.errTok(.pragma_pack_int, tok_i);
135 return null;
136 },
137 }
138}
139
140fn pop(pack: *Pack, p: *Parser, maybe_label: ?[]const u8) void {
141 if (maybe_label) |label| {
142 var i = pack.stack.items.len;
143 while (i > 0) {
144 i -= 1;
145 if (std.mem.eql(u8, pack.stack.items[i].label, label)) {
146 const prev = pack.stack.orderedRemove(i);
147 p.pragma_pack = prev.val;
148 return;
149 }
150 }
151 } else {
152 const prev = pack.stack.popOrNull() orelse {
153 p.pragma_pack = 2;
154 return;
155 };
156 p.pragma_pack = prev.val;
157 }
158}
159
160fn preserveTokens(_: *Pragma, pp: *Preprocessor, start_idx: TokenIndex) bool {
161 _ = pp;
162 _ = start_idx;
163 return true;
164}
lib/compiler/aro/aro/record_layout.zig deleted-669
...@@ -1,669 +0,0 @@
1//! Record layout code adapted from https://github.com/mahkoh/repr-c
2//! Licensed under MIT license: https://github.com/mahkoh/repr-c/tree/master/repc/facade
3
4const std = @import("std");
5const Type = @import("Type.zig");
6const Attribute = @import("Attribute.zig");
7const Compilation = @import("Compilation.zig");
8const Parser = @import("Parser.zig");
9const Record = Type.Record;
10const Field = Record.Field;
11const TypeLayout = Type.TypeLayout;
12const FieldLayout = Type.FieldLayout;
13const target_util = @import("target.zig");
14
15const BITS_PER_BYTE = 8;
16
17const OngoingBitfield = struct {
18 size_bits: u64,
19 unused_size_bits: u64,
20};
21
22pub const Error = error{Overflow};
23
24fn alignForward(addr: u64, alignment: u64) !u64 {
25 const forward_addr = try std.math.add(u64, addr, alignment - 1);
26 return std.mem.alignBackward(u64, forward_addr, alignment);
27}
28
29const SysVContext = struct {
30 /// Does the record have an __attribute__((packed)) annotation.
31 attr_packed: bool,
32 /// The value of #pragma pack(N) at the type level if any.
33 max_field_align_bits: ?u64,
34 /// The alignment of this record.
35 aligned_bits: u32,
36 is_union: bool,
37 /// The size of the record. This might not be a multiple of 8 if the record contains bit-fields.
38 /// For structs, this is also the offset of the first bit after the last field.
39 size_bits: u64,
40 /// non-null if the previous field was a non-zero-sized bit-field. Only used by MinGW.
41 ongoing_bitfield: ?OngoingBitfield,
42
43 comp: *const Compilation,
44
45 fn init(ty: Type, comp: *const Compilation, pragma_pack: ?u8) SysVContext {
46 const pack_value: ?u64 = if (pragma_pack) |pak| @as(u64, pak) * BITS_PER_BYTE else null;
47 const req_align = @as(u32, (ty.requestedAlignment(comp) orelse 1)) * BITS_PER_BYTE;
48 return SysVContext{
49 .attr_packed = ty.hasAttribute(.@"packed"),
50 .max_field_align_bits = pack_value,
51 .aligned_bits = req_align,
52 .is_union = ty.is(.@"union"),
53 .size_bits = 0,
54 .comp = comp,
55 .ongoing_bitfield = null,
56 };
57 }
58
59 fn layoutFields(self: *SysVContext, rec: *const Record) !void {
60 for (rec.fields, 0..) |*fld, fld_indx| {
61 if (fld.ty.specifier == .invalid) continue;
62 const type_layout = computeLayout(fld.ty, self.comp);
63
64 var field_attrs: ?[]const Attribute = null;
65 if (rec.field_attributes) |attrs| {
66 field_attrs = attrs[fld_indx];
67 }
68 if (self.comp.target.isMinGW()) {
69 fld.layout = try self.layoutMinGWField(fld, field_attrs, type_layout);
70 } else {
71 if (fld.isRegularField()) {
72 fld.layout = try self.layoutRegularField(field_attrs, type_layout);
73 } else {
74 fld.layout = try self.layoutBitField(field_attrs, type_layout, fld.isNamed(), fld.specifiedBitWidth());
75 }
76 }
77 }
78 }
79
80 /// On MinGW the alignment of the field is calculated in the usual way except that the alignment of
81 /// the underlying type is ignored in three cases
82 /// - the field is packed
83 /// - the field is a bit-field and the previous field was a non-zero-sized bit-field with the same type size
84 /// - the field is a zero-sized bit-field and the previous field was not a non-zero-sized bit-field
85 /// See test case 0068.
86 fn ignoreTypeAlignment(is_attr_packed: bool, bit_width: ?u32, ongoing_bitfield: ?OngoingBitfield, fld_layout: TypeLayout) bool {
87 if (is_attr_packed) return true;
88 if (bit_width) |width| {
89 if (ongoing_bitfield) |ongoing| {
90 if (ongoing.size_bits == fld_layout.size_bits) return true;
91 } else {
92 if (width == 0) return true;
93 }
94 }
95 return false;
96 }
97
98 fn layoutMinGWField(
99 self: *SysVContext,
100 field: *const Field,
101 field_attrs: ?[]const Attribute,
102 field_layout: TypeLayout,
103 ) !FieldLayout {
104 const annotation_alignment_bits = BITS_PER_BYTE * @as(u32, (Type.annotationAlignment(self.comp, Attribute.Iterator.initSlice(field_attrs)) orelse 1));
105 const is_attr_packed = self.attr_packed or isPacked(field_attrs);
106 const ignore_type_alignment = ignoreTypeAlignment(is_attr_packed, field.bit_width, self.ongoing_bitfield, field_layout);
107
108 var field_alignment_bits: u64 = field_layout.field_alignment_bits;
109 if (ignore_type_alignment) {
110 field_alignment_bits = BITS_PER_BYTE;
111 }
112 field_alignment_bits = @max(field_alignment_bits, annotation_alignment_bits);
113 if (self.max_field_align_bits) |bits| {
114 field_alignment_bits = @min(field_alignment_bits, bits);
115 }
116
117 // The field affects the record alignment in one of three cases
118 // - the field is a regular field
119 // - the field is a zero-width bit-field following a non-zero-width bit-field
120 // - the field is a non-zero-width bit-field and not packed.
121 // See test case 0069.
122 const update_record_alignment =
123 field.isRegularField() or
124 (field.specifiedBitWidth() == 0 and self.ongoing_bitfield != null) or
125 (field.specifiedBitWidth() != 0 and !is_attr_packed);
126
127 // If a field affects the alignment of a record, the alignment is calculated in the
128 // usual way except that __attribute__((packed)) is ignored on a zero-width bit-field.
129 // See test case 0068.
130 if (update_record_alignment) {
131 var ty_alignment_bits = field_layout.field_alignment_bits;
132 if (is_attr_packed and (field.isRegularField() or field.specifiedBitWidth() != 0)) {
133 ty_alignment_bits = BITS_PER_BYTE;
134 }
135 ty_alignment_bits = @max(ty_alignment_bits, annotation_alignment_bits);
136 if (self.max_field_align_bits) |bits| {
137 ty_alignment_bits = @intCast(@min(ty_alignment_bits, bits));
138 }
139 self.aligned_bits = @max(self.aligned_bits, ty_alignment_bits);
140 }
141
142 // NOTE: ty_alignment_bits and field_alignment_bits are different in the following case:
143 // Y = { size: 64, alignment: 64 }struct {
144 // { offset: 0, size: 1 }c { size: 8, alignment: 8 }char:1,
145 // @attr_packed _ { size: 64, alignment: 64 }long long:0,
146 // { offset: 8, size: 8 }d { size: 8, alignment: 8 }char,
147 // }
148 if (field.isRegularField()) {
149 return self.layoutRegularFieldMinGW(field_layout.size_bits, field_alignment_bits);
150 } else {
151 return self.layoutBitFieldMinGW(field_layout.size_bits, field_alignment_bits, field.isNamed(), field.specifiedBitWidth());
152 }
153 }
154
155 fn layoutBitFieldMinGW(
156 self: *SysVContext,
157 ty_size_bits: u64,
158 field_alignment_bits: u64,
159 is_named: bool,
160 width: u64,
161 ) !FieldLayout {
162 std.debug.assert(width <= ty_size_bits); // validated in parser
163
164 // In a union, the size of the underlying type does not affect the size of the union.
165 // See test case 0070.
166 if (self.is_union) {
167 self.size_bits = @max(self.size_bits, width);
168 if (!is_named) return .{};
169 return .{
170 .offset_bits = 0,
171 .size_bits = width,
172 };
173 }
174 if (width == 0) {
175 self.ongoing_bitfield = null;
176 } else {
177 // If there is an ongoing bit-field in a struct whose underlying type has the same size and
178 // if there is enough space left to place this bit-field, then this bit-field is placed in
179 // the ongoing bit-field and the size of the struct is not affected by this
180 // bit-field. See test case 0037.
181 if (self.ongoing_bitfield) |*ongoing| {
182 if (ongoing.size_bits == ty_size_bits and ongoing.unused_size_bits >= width) {
183 const offset_bits = self.size_bits - ongoing.unused_size_bits;
184 ongoing.unused_size_bits -= width;
185 if (!is_named) return .{};
186 return .{
187 .offset_bits = offset_bits,
188 .size_bits = width,
189 };
190 }
191 }
192 // Otherwise this field is part of a new ongoing bit-field.
193 self.ongoing_bitfield = .{
194 .size_bits = ty_size_bits,
195 .unused_size_bits = ty_size_bits - width,
196 };
197 }
198 const offset_bits = try alignForward(self.size_bits, field_alignment_bits);
199 self.size_bits = if (width == 0) offset_bits else try std.math.add(u64, offset_bits, ty_size_bits);
200 if (!is_named) return .{};
201 return .{
202 .offset_bits = offset_bits,
203 .size_bits = width,
204 };
205 }
206
207 fn layoutRegularFieldMinGW(
208 self: *SysVContext,
209 ty_size_bits: u64,
210 field_alignment_bits: u64,
211 ) !FieldLayout {
212 self.ongoing_bitfield = null;
213 // A struct field starts at the next offset in the struct that is properly
214 // aligned with respect to the start of the struct. See test case 0033.
215 // A union field always starts at offset 0.
216 const offset_bits = if (self.is_union) 0 else try alignForward(self.size_bits, field_alignment_bits);
217
218 // Set the size of the record to the maximum of the current size and the end of
219 // the field. See test case 0034.
220 self.size_bits = @max(self.size_bits, try std.math.add(u64, offset_bits, ty_size_bits));
221
222 return .{
223 .offset_bits = offset_bits,
224 .size_bits = ty_size_bits,
225 };
226 }
227
228 fn layoutRegularField(
229 self: *SysVContext,
230 fld_attrs: ?[]const Attribute,
231 fld_layout: TypeLayout,
232 ) !FieldLayout {
233 var fld_align_bits = fld_layout.field_alignment_bits;
234
235 // If the struct or the field is packed, then the alignment of the underlying type is
236 // ignored. See test case 0084.
237 if (self.attr_packed or isPacked(fld_attrs)) {
238 fld_align_bits = BITS_PER_BYTE;
239 }
240
241 // The field alignment can be increased by __attribute__((aligned)) annotations on the
242 // field. See test case 0085.
243 if (Type.annotationAlignment(self.comp, Attribute.Iterator.initSlice(fld_attrs))) |anno| {
244 fld_align_bits = @max(fld_align_bits, @as(u32, anno) * BITS_PER_BYTE);
245 }
246
247 // #pragma pack takes precedence over all other attributes. See test cases 0084 and
248 // 0085.
249 if (self.max_field_align_bits) |req_bits| {
250 fld_align_bits = @intCast(@min(fld_align_bits, req_bits));
251 }
252
253 // A struct field starts at the next offset in the struct that is properly
254 // aligned with respect to the start of the struct.
255 const offset_bits = if (self.is_union) 0 else try alignForward(self.size_bits, fld_align_bits);
256 const size_bits = fld_layout.size_bits;
257
258 // The alignment of a record is the maximum of its field alignments. See test cases
259 // 0084, 0085, 0086.
260 self.size_bits = @max(self.size_bits, try std.math.add(u64, offset_bits, size_bits));
261 self.aligned_bits = @max(self.aligned_bits, fld_align_bits);
262
263 return .{
264 .offset_bits = offset_bits,
265 .size_bits = size_bits,
266 };
267 }
268
269 fn layoutBitField(
270 self: *SysVContext,
271 fld_attrs: ?[]const Attribute,
272 fld_layout: TypeLayout,
273 is_named: bool,
274 bit_width: u64,
275 ) !FieldLayout {
276 const ty_size_bits = fld_layout.size_bits;
277 var ty_fld_algn_bits: u32 = fld_layout.field_alignment_bits;
278
279 if (bit_width > 0) {
280 std.debug.assert(bit_width <= ty_size_bits); // Checked in parser
281 // Some targets ignore the alignment of the underlying type when laying out
282 // non-zero-sized bit-fields. See test case 0072. On such targets, bit-fields never
283 // cross a storage boundary. See test case 0081.
284 if (target_util.ignoreNonZeroSizedBitfieldTypeAlignment(self.comp.target)) {
285 ty_fld_algn_bits = 1;
286 }
287 } else {
288 // Some targets ignore the alignment of the underlying type when laying out
289 // zero-sized bit-fields. See test case 0073.
290 if (target_util.ignoreZeroSizedBitfieldTypeAlignment(self.comp.target)) {
291 ty_fld_algn_bits = 1;
292 }
293 // Some targets have a minimum alignment of zero-sized bit-fields. See test case
294 // 0074.
295 if (target_util.minZeroWidthBitfieldAlignment(self.comp.target)) |target_align| {
296 ty_fld_algn_bits = @max(ty_fld_algn_bits, target_align);
297 }
298 }
299
300 // __attribute__((packed)) on the record is identical to __attribute__((packed)) on each
301 // field. See test case 0067.
302 const attr_packed = self.attr_packed or isPacked(fld_attrs);
303 const has_packing_annotation = attr_packed or self.max_field_align_bits != null;
304
305 const annotation_alignment = if (Type.annotationAlignment(self.comp, Attribute.Iterator.initSlice(fld_attrs))) |anno| @as(u32, anno) * BITS_PER_BYTE else 1;
306
307 const first_unused_bit: u64 = if (self.is_union) 0 else self.size_bits;
308 var field_align_bits: u64 = 1;
309
310 if (bit_width == 0) {
311 field_align_bits = @max(ty_fld_algn_bits, annotation_alignment);
312 } else if (self.comp.langopts.emulate == .gcc) {
313 // On GCC, the field alignment is at least the alignment requested by annotations
314 // except as restricted by #pragma pack. See test case 0083.
315 field_align_bits = annotation_alignment;
316 if (self.max_field_align_bits) |max_bits| {
317 field_align_bits = @min(annotation_alignment, max_bits);
318 }
319
320 // On GCC, if there are no packing annotations and
321 // - the field would otherwise start at an offset such that it would cross a
322 // storage boundary or
323 // - the alignment of the type is larger than its size,
324 // then it is aligned to the type's field alignment. See test case 0083.
325 if (!has_packing_annotation) {
326 const start_bit = try alignForward(first_unused_bit, field_align_bits);
327
328 const does_field_cross_boundary = start_bit % ty_fld_algn_bits + bit_width > ty_size_bits;
329
330 if (ty_fld_algn_bits > ty_size_bits or does_field_cross_boundary) {
331 field_align_bits = @max(field_align_bits, ty_fld_algn_bits);
332 }
333 }
334 } else {
335 std.debug.assert(self.comp.langopts.emulate == .clang);
336
337 // On Clang, the alignment requested by annotations is not respected if it is
338 // larger than the value of #pragma pack. See test case 0083.
339 if (annotation_alignment <= self.max_field_align_bits orelse std.math.maxInt(u29)) {
340 field_align_bits = @max(field_align_bits, annotation_alignment);
341 }
342 // On Clang, if there are no packing annotations and the field would cross a
343 // storage boundary if it were positioned at the first unused bit in the record,
344 // it is aligned to the type's field alignment. See test case 0083.
345 if (!has_packing_annotation) {
346 const does_field_cross_boundary = first_unused_bit % ty_fld_algn_bits + bit_width > ty_size_bits;
347
348 if (does_field_cross_boundary)
349 field_align_bits = @max(field_align_bits, ty_fld_algn_bits);
350 }
351 }
352
353 const offset_bits = try alignForward(first_unused_bit, field_align_bits);
354 self.size_bits = @max(self.size_bits, try std.math.add(u64, offset_bits, bit_width));
355
356 // Unnamed fields do not contribute to the record alignment except on a few targets.
357 // See test case 0079.
358 if (is_named or target_util.unnamedFieldAffectsAlignment(self.comp.target)) {
359 var inherited_align_bits: u32 = undefined;
360
361 if (bit_width == 0) {
362 // If the width is 0, #pragma pack and __attribute__((packed)) are ignored.
363 // See test case 0075.
364 inherited_align_bits = @max(ty_fld_algn_bits, annotation_alignment);
365 } else if (self.max_field_align_bits) |max_align_bits| {
366 // Otherwise, if a #pragma pack is in effect, __attribute__((packed)) on the field or
367 // record is ignored. See test case 0076.
368 inherited_align_bits = @max(ty_fld_algn_bits, annotation_alignment);
369 inherited_align_bits = @intCast(@min(inherited_align_bits, max_align_bits));
370 } else if (attr_packed) {
371 // Otherwise, if the field or the record is packed, the field alignment is 1 bit unless
372 // it is explicitly increased with __attribute__((aligned)). See test case 0077.
373 inherited_align_bits = annotation_alignment;
374 } else {
375 // Otherwise, the field alignment is the field alignment of the underlying type unless
376 // it is explicitly increased with __attribute__((aligned)). See test case 0078.
377 inherited_align_bits = @max(ty_fld_algn_bits, annotation_alignment);
378 }
379 self.aligned_bits = @max(self.aligned_bits, inherited_align_bits);
380 }
381
382 if (!is_named) return .{};
383 return .{
384 .size_bits = bit_width,
385 .offset_bits = offset_bits,
386 };
387 }
388};
389
390const MsvcContext = struct {
391 req_align_bits: u32,
392 max_field_align_bits: ?u32,
393 /// The alignment of pointers that point to an object of this type. This is greater than or equal
394 /// to the required alignment. Once all fields have been laid out, the size of the record will be
395 /// rounded up to this value.
396 pointer_align_bits: u32,
397 /// The alignment of this type when it is used as a record field. This is greater than or equal to
398 /// the pointer alignment.
399 field_align_bits: u32,
400 size_bits: u64,
401 ongoing_bitfield: ?OngoingBitfield,
402 contains_non_bitfield: bool,
403 is_union: bool,
404 comp: *const Compilation,
405
406 fn init(ty: Type, comp: *const Compilation, pragma_pack: ?u8) MsvcContext {
407 var pack_value: ?u32 = null;
408 if (ty.hasAttribute(.@"packed")) {
409 // __attribute__((packed)) behaves like #pragma pack(1) in clang. See test case 0056.
410 pack_value = BITS_PER_BYTE;
411 }
412 if (pack_value == null) {
413 if (pragma_pack) |pack| {
414 pack_value = pack * BITS_PER_BYTE;
415 }
416 }
417 if (pack_value) |pack| {
418 pack_value = msvcPragmaPack(comp, pack);
419 }
420
421 // The required alignment can be increased by adding a __declspec(align)
422 // annotation. See test case 0023.
423 const must_align = @as(u32, (ty.requestedAlignment(comp) orelse 1)) * BITS_PER_BYTE;
424 return MsvcContext{
425 .req_align_bits = must_align,
426 .pointer_align_bits = must_align,
427 .field_align_bits = must_align,
428 .size_bits = 0,
429 .max_field_align_bits = pack_value,
430 .ongoing_bitfield = null,
431 .contains_non_bitfield = false,
432 .is_union = ty.is(.@"union"),
433 .comp = comp,
434 };
435 }
436
437 fn layoutField(self: *MsvcContext, fld: *const Field, fld_attrs: ?[]const Attribute) !FieldLayout {
438 const type_layout = computeLayout(fld.ty, self.comp);
439
440 // The required alignment of the field is the maximum of the required alignment of the
441 // underlying type and the __declspec(align) annotation on the field itself.
442 // See test case 0028.
443 var req_align = type_layout.required_alignment_bits;
444 if (Type.annotationAlignment(self.comp, Attribute.Iterator.initSlice(fld_attrs))) |anno| {
445 req_align = @max(@as(u32, anno) * BITS_PER_BYTE, req_align);
446 }
447
448 // The required alignment of a record is the maximum of the required alignments of its
449 // fields except that the required alignment of bitfields is ignored.
450 // See test case 0029.
451 if (fld.isRegularField()) {
452 self.req_align_bits = @max(self.req_align_bits, req_align);
453 }
454
455 // The offset of the field is based on the field alignment of the underlying type.
456 // See test case 0027.
457 var fld_align_bits = type_layout.field_alignment_bits;
458 if (self.max_field_align_bits) |max_align| {
459 fld_align_bits = @min(fld_align_bits, max_align);
460 }
461 // check the requested alignment of the field type.
462 if (fld.ty.requestedAlignment(self.comp)) |type_req_align| {
463 fld_align_bits = @max(fld_align_bits, type_req_align * 8);
464 }
465
466 if (isPacked(fld_attrs)) {
467 // __attribute__((packed)) on a field is a clang extension. It behaves as if #pragma
468 // pack(1) had been applied only to this field. See test case 0057.
469 fld_align_bits = BITS_PER_BYTE;
470 }
471 // __attribute__((packed)) on a field is a clang extension. It behaves as if #pragma
472 // pack(1) had been applied only to this field. See test case 0057.
473 fld_align_bits = @max(fld_align_bits, req_align);
474 if (fld.isRegularField()) {
475 return self.layoutRegularField(type_layout.size_bits, fld_align_bits);
476 } else {
477 return self.layoutBitField(type_layout.size_bits, fld_align_bits, fld.specifiedBitWidth());
478 }
479 }
480
481 fn layoutBitField(self: *MsvcContext, ty_size_bits: u64, field_align: u32, bit_width: u32) !FieldLayout {
482 if (bit_width == 0) {
483 // A zero-sized bit-field that does not follow a non-zero-sized bit-field does not affect
484 // the overall layout of the record. Even in a union where the order would otherwise
485 // not matter. See test case 0035.
486 if (self.ongoing_bitfield) |_| {
487 self.ongoing_bitfield = null;
488 } else {
489 // this field takes 0 space.
490 return .{ .offset_bits = self.size_bits, .size_bits = bit_width };
491 }
492 } else {
493 std.debug.assert(bit_width <= ty_size_bits);
494 // If there is an ongoing bit-field in a struct whose underlying type has the same size and
495 // if there is enough space left to place this bit-field, then this bit-field is placed in
496 // the ongoing bit-field and the overall layout of the struct is not affected by this
497 // bit-field. See test case 0037.
498 if (!self.is_union) {
499 if (self.ongoing_bitfield) |*p| {
500 if (p.size_bits == ty_size_bits and p.unused_size_bits >= bit_width) {
501 const offset_bits = self.size_bits - p.unused_size_bits;
502 p.unused_size_bits -= bit_width;
503 return .{ .offset_bits = offset_bits, .size_bits = bit_width };
504 }
505 }
506 }
507 // Otherwise this field is part of a new ongoing bit-field.
508 self.ongoing_bitfield = .{ .size_bits = ty_size_bits, .unused_size_bits = ty_size_bits - bit_width };
509 }
510 const offset_bits = if (!self.is_union) bits: {
511 // This is the one place in the layout of a record where the pointer alignment might
512 // get assigned a smaller value than the field alignment. This can only happen if
513 // the field or the type of the field has a required alignment. Otherwise the value
514 // of field_alignment_bits is already bound by max_field_alignment_bits.
515 // See test case 0038.
516 const p_align = if (self.max_field_align_bits) |max_fld_align|
517 @min(max_fld_align, field_align)
518 else
519 field_align;
520 self.pointer_align_bits = @max(self.pointer_align_bits, p_align);
521 self.field_align_bits = @max(self.field_align_bits, field_align);
522
523 const offset_bits = try alignForward(self.size_bits, field_align);
524 self.size_bits = if (bit_width == 0) offset_bits else offset_bits + ty_size_bits;
525
526 break :bits offset_bits;
527 } else bits: {
528 // Bit-fields do not affect the alignment of a union. See test case 0041.
529 self.size_bits = @max(self.size_bits, ty_size_bits);
530 break :bits 0;
531 };
532 return .{ .offset_bits = offset_bits, .size_bits = bit_width };
533 }
534
535 fn layoutRegularField(self: *MsvcContext, size_bits: u64, field_align: u32) !FieldLayout {
536 self.contains_non_bitfield = true;
537 self.ongoing_bitfield = null;
538 // The alignment of the field affects both the pointer alignment and the field
539 // alignment of the record. See test case 0032.
540 self.pointer_align_bits = @max(self.pointer_align_bits, field_align);
541 self.field_align_bits = @max(self.field_align_bits, field_align);
542 const offset_bits = switch (self.is_union) {
543 true => 0,
544 false => try alignForward(self.size_bits, field_align),
545 };
546 self.size_bits = @max(self.size_bits, offset_bits + size_bits);
547 return .{ .offset_bits = offset_bits, .size_bits = size_bits };
548 }
549 fn handleZeroSizedRecord(self: *MsvcContext) void {
550 if (self.is_union) {
551 // MSVC does not allow unions without fields.
552 // If all fields in a union have size 0, the size of the union is set to
553 // - its field alignment if it contains at least one non-bitfield
554 // - 4 bytes if it contains only bitfields
555 // See test case 0025.
556 if (self.contains_non_bitfield) {
557 self.size_bits = self.field_align_bits;
558 } else {
559 self.size_bits = 4 * BITS_PER_BYTE;
560 }
561 } else {
562 // If all fields in a struct have size 0, its size is set to its required alignment
563 // but at least to 4 bytes. See test case 0026.
564 self.size_bits = @max(self.req_align_bits, 4 * BITS_PER_BYTE);
565 self.pointer_align_bits = @intCast(@min(self.pointer_align_bits, self.size_bits));
566 }
567 }
568};
569
570pub fn compute(rec: *Type.Record, ty: Type, comp: *const Compilation, pragma_pack: ?u8) Error!void {
571 switch (comp.langopts.emulate) {
572 .gcc, .clang => {
573 var context = SysVContext.init(ty, comp, pragma_pack);
574
575 try context.layoutFields(rec);
576
577 context.size_bits = try alignForward(context.size_bits, context.aligned_bits);
578
579 rec.type_layout = .{
580 .size_bits = context.size_bits,
581 .field_alignment_bits = context.aligned_bits,
582 .pointer_alignment_bits = context.aligned_bits,
583 .required_alignment_bits = BITS_PER_BYTE,
584 };
585 },
586 .msvc => {
587 var context = MsvcContext.init(ty, comp, pragma_pack);
588 for (rec.fields, 0..) |*fld, fld_indx| {
589 if (fld.ty.specifier == .invalid) continue;
590 var field_attrs: ?[]const Attribute = null;
591 if (rec.field_attributes) |attrs| {
592 field_attrs = attrs[fld_indx];
593 }
594
595 fld.layout = try context.layoutField(fld, field_attrs);
596 }
597 if (context.size_bits == 0) {
598 // As an extension, MSVC allows records that only contain zero-sized bitfields and empty
599 // arrays. Such records would be zero-sized but this case is handled here separately to
600 // ensure that there are no zero-sized records.
601 context.handleZeroSizedRecord();
602 }
603 context.size_bits = try alignForward(context.size_bits, context.pointer_align_bits);
604 rec.type_layout = .{
605 .size_bits = context.size_bits,
606 .field_alignment_bits = context.field_align_bits,
607 .pointer_alignment_bits = context.pointer_align_bits,
608 .required_alignment_bits = context.req_align_bits,
609 };
610 },
611 }
612}
613
614fn computeLayout(ty: Type, comp: *const Compilation) TypeLayout {
615 if (ty.getRecord()) |rec| {
616 const requested = BITS_PER_BYTE * (ty.requestedAlignment(comp) orelse 0);
617 return .{
618 .size_bits = rec.type_layout.size_bits,
619 .pointer_alignment_bits = @max(requested, rec.type_layout.pointer_alignment_bits),
620 .field_alignment_bits = @max(requested, rec.type_layout.field_alignment_bits),
621 .required_alignment_bits = rec.type_layout.required_alignment_bits,
622 };
623 } else {
624 const type_align = ty.alignof(comp) * BITS_PER_BYTE;
625 return .{
626 .size_bits = ty.bitSizeof(comp) orelse 0,
627 .pointer_alignment_bits = type_align,
628 .field_alignment_bits = type_align,
629 .required_alignment_bits = BITS_PER_BYTE,
630 };
631 }
632}
633
634fn isPacked(attrs: ?[]const Attribute) bool {
635 const a = attrs orelse return false;
636
637 for (a) |attribute| {
638 if (attribute.tag != .@"packed") continue;
639 return true;
640 }
641 return false;
642}
643
644// The effect of #pragma pack(N) depends on the target.
645//
646// x86: By default, there is no maximum field alignment. N={1,2,4} set the maximum field
647// alignment to that value. All other N activate the default.
648// x64: By default, there is no maximum field alignment. N={1,2,4,8} set the maximum field
649// alignment to that value. All other N activate the default.
650// arm: By default, the maximum field alignment is 8. N={1,2,4,8,16} set the maximum field
651// alignment to that value. All other N activate the default.
652// arm64: By default, the maximum field alignment is 8. N={1,2,4,8} set the maximum field
653// alignment to that value. N=16 disables the maximum field alignment. All other N
654// activate the default.
655//
656// See test case 0020.
657pub fn msvcPragmaPack(comp: *const Compilation, pack: u32) ?u32 {
658 return switch (pack) {
659 8, 16, 32 => pack,
660 64 => if (comp.target.cpu.arch == .x86) null else pack,
661 128 => if (comp.target.cpu.arch == .thumb) pack else null,
662 else => {
663 return switch (comp.target.cpu.arch) {
664 .thumb, .aarch64 => 64,
665 else => null,
666 };
667 },
668 };
669}
lib/compiler/aro/aro/target.zig deleted-782
...@@ -1,782 +0,0 @@
1const std = @import("std");
2const LangOpts = @import("LangOpts.zig");
3const Type = @import("Type.zig");
4const TargetSet = @import("Builtins/Properties.zig").TargetSet;
5
6/// intmax_t for this target
7pub fn intMaxType(target: std.Target) Type {
8 switch (target.cpu.arch) {
9 .aarch64,
10 .aarch64_be,
11 .sparc64,
12 => if (target.os.tag != .openbsd) return .{ .specifier = .long },
13
14 .bpfel,
15 .bpfeb,
16 .loongarch64,
17 .riscv64,
18 .powerpc64,
19 .powerpc64le,
20 .ve,
21 => return .{ .specifier = .long },
22
23 .x86_64 => switch (target.os.tag) {
24 .windows, .openbsd => {},
25 else => switch (target.abi) {
26 .gnux32, .muslx32 => {},
27 else => return .{ .specifier = .long },
28 },
29 },
30
31 else => {},
32 }
33 return .{ .specifier = .long_long };
34}
35
36/// intptr_t for this target
37pub fn intPtrType(target: std.Target) Type {
38 if (target.os.tag == .haiku) return .{ .specifier = .long };
39
40 switch (target.cpu.arch) {
41 .aarch64, .aarch64_be => switch (target.os.tag) {
42 .windows => return .{ .specifier = .long_long },
43 else => {},
44 },
45
46 .msp430,
47 .csky,
48 .loongarch32,
49 .riscv32,
50 .xcore,
51 .hexagon,
52 .m68k,
53 .spirv32,
54 .arc,
55 .avr,
56 => return .{ .specifier = .int },
57
58 .sparc => switch (target.os.tag) {
59 .netbsd, .openbsd => {},
60 else => return .{ .specifier = .int },
61 },
62
63 .powerpc, .powerpcle => switch (target.os.tag) {
64 .linux, .freebsd, .netbsd => return .{ .specifier = .int },
65 else => {},
66 },
67
68 // 32-bit x86 Darwin, OpenBSD, and RTEMS use long (the default); others use int
69 .x86 => switch (target.os.tag) {
70 .openbsd, .rtems => {},
71 else => if (!target.os.tag.isDarwin()) return .{ .specifier = .int },
72 },
73
74 .x86_64 => switch (target.os.tag) {
75 .windows => return .{ .specifier = .long_long },
76 else => switch (target.abi) {
77 .gnux32, .muslx32 => return .{ .specifier = .int },
78 else => {},
79 },
80 },
81
82 else => {},
83 }
84
85 return .{ .specifier = .long };
86}
87
88/// int16_t for this target
89pub fn int16Type(target: std.Target) Type {
90 return switch (target.cpu.arch) {
91 .avr => .{ .specifier = .int },
92 else => .{ .specifier = .short },
93 };
94}
95
96/// sig_atomic_t for this target
97pub fn sigAtomicType(target: std.Target) Type {
98 if (target.cpu.arch.isWasm()) return .{ .specifier = .long };
99 return switch (target.cpu.arch) {
100 .avr => .{ .specifier = .schar },
101 .msp430 => .{ .specifier = .long },
102 else => .{ .specifier = .int },
103 };
104}
105
106/// int64_t for this target
107pub fn int64Type(target: std.Target) Type {
108 switch (target.cpu.arch) {
109 .loongarch64,
110 .ve,
111 .riscv64,
112 .powerpc64,
113 .powerpc64le,
114 .bpfel,
115 .bpfeb,
116 => return .{ .specifier = .long },
117
118 .sparc64 => return intMaxType(target),
119
120 .x86, .x86_64 => if (!target.isDarwin()) return intMaxType(target),
121 .aarch64, .aarch64_be => if (!target.isDarwin() and target.os.tag != .openbsd and target.os.tag != .windows) return .{ .specifier = .long },
122 else => {},
123 }
124 return .{ .specifier = .long_long };
125}
126
127pub fn float80Type(target: std.Target) ?Type {
128 switch (target.cpu.arch) {
129 .x86, .x86_64 => return .{ .specifier = .long_double },
130 else => {},
131 }
132 return null;
133}
134
135/// This function returns 1 if function alignment is not observable or settable.
136pub fn defaultFunctionAlignment(target: std.Target) u8 {
137 return switch (target.cpu.arch) {
138 .arm, .armeb => 4,
139 .aarch64, .aarch64_be => 4,
140 .sparc, .sparc64 => 4,
141 .riscv64 => 2,
142 else => 1,
143 };
144}
145
146pub fn isTlsSupported(target: std.Target) bool {
147 if (target.isDarwin()) {
148 var supported = false;
149 switch (target.os.tag) {
150 .macos => supported = !(target.os.isAtLeast(.macos, .{ .major = 10, .minor = 7, .patch = 0 }) orelse false),
151 else => {},
152 }
153 return supported;
154 }
155 return switch (target.cpu.arch) {
156 .bpfel, .bpfeb, .msp430, .nvptx, .nvptx64, .x86, .arm, .armeb, .thumb, .thumbeb => false,
157 else => true,
158 };
159}
160
161pub fn ignoreNonZeroSizedBitfieldTypeAlignment(target: std.Target) bool {
162 switch (target.cpu.arch) {
163 .avr => return true,
164 .arm => {
165 if (std.Target.arm.featureSetHas(target.cpu.features, .has_v7)) {
166 switch (target.os.tag) {
167 .ios => return true,
168 else => return false,
169 }
170 }
171 },
172 else => return false,
173 }
174 return false;
175}
176
177pub fn ignoreZeroSizedBitfieldTypeAlignment(target: std.Target) bool {
178 switch (target.cpu.arch) {
179 .avr => return true,
180 else => return false,
181 }
182}
183
184pub fn minZeroWidthBitfieldAlignment(target: std.Target) ?u29 {
185 switch (target.cpu.arch) {
186 .avr => return 8,
187 .arm => {
188 if (std.Target.arm.featureSetHas(target.cpu.features, .has_v7)) {
189 switch (target.os.tag) {
190 .ios => return 32,
191 else => return null,
192 }
193 } else return null;
194 },
195 else => return null,
196 }
197}
198
199pub fn unnamedFieldAffectsAlignment(target: std.Target) bool {
200 switch (target.cpu.arch) {
201 .aarch64 => {
202 if (target.isDarwin() or target.os.tag == .windows) return false;
203 return true;
204 },
205 .armeb => {
206 if (std.Target.arm.featureSetHas(target.cpu.features, .has_v7)) {
207 if (std.Target.Abi.default(target.cpu.arch, target.os) == .eabi) return true;
208 }
209 },
210 .arm => return true,
211 .avr => return true,
212 .thumb => {
213 if (target.os.tag == .windows) return false;
214 return true;
215 },
216 else => return false,
217 }
218 return false;
219}
220
221pub fn packAllEnums(target: std.Target) bool {
222 return switch (target.cpu.arch) {
223 .hexagon => true,
224 else => false,
225 };
226}
227
228/// Default alignment (in bytes) for __attribute__((aligned)) when no alignment is specified
229pub fn defaultAlignment(target: std.Target) u29 {
230 switch (target.cpu.arch) {
231 .avr => return 1,
232 .arm => if (target.isAndroid() or target.os.tag == .ios) return 16 else return 8,
233 .sparc => if (std.Target.sparc.featureSetHas(target.cpu.features, .v9)) return 16 else return 8,
234 .mips, .mipsel => switch (target.abi) {
235 .none, .gnuabi64 => return 16,
236 else => return 8,
237 },
238 .s390x, .armeb, .thumbeb, .thumb => return 8,
239 else => return 16,
240 }
241}
242pub fn systemCompiler(target: std.Target) LangOpts.Compiler {
243 // Android is linux but not gcc, so these checks go first
244 // the rest for documentation as fn returns .clang
245 if (target.isDarwin() or
246 target.isAndroid() or
247 target.isBSD() or
248 target.os.tag == .fuchsia or
249 target.os.tag == .solaris or
250 target.os.tag == .haiku or
251 target.cpu.arch == .hexagon)
252 {
253 return .clang;
254 }
255 if (target.os.tag == .uefi) return .msvc;
256 // this is before windows to grab WindowsGnu
257 if (target.abi.isGnu() or
258 target.os.tag == .linux)
259 {
260 return .gcc;
261 }
262 if (target.os.tag == .windows) {
263 return .msvc;
264 }
265 if (target.cpu.arch == .avr) return .gcc;
266 return .clang;
267}
268
269pub fn hasFloat128(target: std.Target) bool {
270 if (target.cpu.arch.isWasm()) return true;
271 if (target.isDarwin()) return false;
272 if (target.cpu.arch.isPowerPC()) return std.Target.powerpc.featureSetHas(target.cpu.features, .float128);
273 return switch (target.os.tag) {
274 .dragonfly,
275 .haiku,
276 .linux,
277 .openbsd,
278 .solaris,
279 => target.cpu.arch.isX86(),
280 else => false,
281 };
282}
283
284pub fn hasInt128(target: std.Target) bool {
285 if (target.cpu.arch == .wasm32) return true;
286 if (target.cpu.arch == .x86_64) return true;
287 return target.ptrBitWidth() >= 64;
288}
289
290pub fn hasHalfPrecisionFloatABI(target: std.Target) bool {
291 return switch (target.cpu.arch) {
292 .thumb, .thumbeb, .arm, .aarch64 => true,
293 else => false,
294 };
295}
296
297pub const FPSemantics = enum {
298 None,
299 IEEEHalf,
300 BFloat,
301 IEEESingle,
302 IEEEDouble,
303 IEEEQuad,
304 /// Minifloat 5-bit exponent 2-bit mantissa
305 E5M2,
306 /// Minifloat 4-bit exponent 3-bit mantissa
307 E4M3,
308 x87ExtendedDouble,
309 IBMExtendedDouble,
310
311 /// Only intended for generating float.h macros for the preprocessor
312 pub fn forType(ty: std.Target.CType, target: std.Target) FPSemantics {
313 std.debug.assert(ty == .float or ty == .double or ty == .longdouble);
314 return switch (target.cTypeBitSize(ty)) {
315 32 => .IEEESingle,
316 64 => .IEEEDouble,
317 80 => .x87ExtendedDouble,
318 128 => switch (target.cpu.arch) {
319 .powerpc, .powerpcle, .powerpc64, .powerpc64le => .IBMExtendedDouble,
320 else => .IEEEQuad,
321 },
322 else => unreachable,
323 };
324 }
325
326 pub fn halfPrecisionType(target: std.Target) ?FPSemantics {
327 switch (target.cpu.arch) {
328 .aarch64,
329 .aarch64_be,
330 .arm,
331 .armeb,
332 .hexagon,
333 .riscv32,
334 .riscv64,
335 .spirv32,
336 .spirv64,
337 => return .IEEEHalf,
338 .x86, .x86_64 => if (std.Target.x86.featureSetHas(target.cpu.features, .sse2)) return .IEEEHalf,
339 else => {},
340 }
341 return null;
342 }
343
344 pub fn chooseValue(self: FPSemantics, comptime T: type, values: [6]T) T {
345 return switch (self) {
346 .IEEEHalf => values[0],
347 .IEEESingle => values[1],
348 .IEEEDouble => values[2],
349 .x87ExtendedDouble => values[3],
350 .IBMExtendedDouble => values[4],
351 .IEEEQuad => values[5],
352 else => unreachable,
353 };
354 }
355};
356
357pub fn isLP64(target: std.Target) bool {
358 return target.cTypeBitSize(.int) == 32 and target.ptrBitWidth() == 64;
359}
360
361pub fn isKnownWindowsMSVCEnvironment(target: std.Target) bool {
362 return target.os.tag == .windows and target.abi == .msvc;
363}
364
365pub fn isWindowsMSVCEnvironment(target: std.Target) bool {
366 return target.os.tag == .windows and (target.abi == .msvc or target.abi == .none);
367}
368
369pub fn isCygwinMinGW(target: std.Target) bool {
370 return target.os.tag == .windows and (target.abi == .gnu or target.abi == .cygnus);
371}
372
373pub fn builtinEnabled(target: std.Target, enabled_for: TargetSet) bool {
374 var it = enabled_for.iterator();
375 while (it.next()) |val| {
376 switch (val) {
377 .basic => return true,
378 .x86_64 => if (target.cpu.arch == .x86_64) return true,
379 .aarch64 => if (target.cpu.arch == .aarch64) return true,
380 .arm => if (target.cpu.arch == .arm) return true,
381 .ppc => switch (target.cpu.arch) {
382 .powerpc, .powerpc64, .powerpc64le => return true,
383 else => {},
384 },
385 else => {
386 // Todo: handle other target predicates
387 },
388 }
389 }
390 return false;
391}
392
393pub fn defaultFpEvalMethod(target: std.Target) LangOpts.FPEvalMethod {
394 if (target.os.tag == .aix) return .double;
395 switch (target.cpu.arch) {
396 .x86, .x86_64 => {
397 if (target.ptrBitWidth() == 32 and target.os.tag == .netbsd) {
398 if (target.os.version_range.semver.min.order(.{ .major = 6, .minor = 99, .patch = 26 }) != .gt) {
399 // NETBSD <= 6.99.26 on 32-bit x86 defaults to double
400 return .double;
401 }
402 }
403 if (std.Target.x86.featureSetHas(target.cpu.features, .sse)) {
404 return .source;
405 }
406 return .extended;
407 },
408 else => {},
409 }
410 return .source;
411}
412
413/// Value of the `-m` flag for `ld` for this target
414pub fn ldEmulationOption(target: std.Target, arm_endianness: ?std.builtin.Endian) ?[]const u8 {
415 return switch (target.cpu.arch) {
416 .x86 => if (target.os.tag == .elfiamcu) "elf_iamcu" else "elf_i386",
417 .arm,
418 .armeb,
419 .thumb,
420 .thumbeb,
421 => switch (arm_endianness orelse target.cpu.arch.endian()) {
422 .little => "armelf_linux_eabi",
423 .big => "armelfb_linux_eabi",
424 },
425 .aarch64 => "aarch64linux",
426 .aarch64_be => "aarch64linuxb",
427 .m68k => "m68kelf",
428 .powerpc => if (target.os.tag == .linux) "elf32ppclinux" else "elf32ppc",
429 .powerpcle => if (target.os.tag == .linux) "elf32lppclinux" else "elf32lppc",
430 .powerpc64 => "elf64ppc",
431 .powerpc64le => "elf64lppc",
432 .riscv32 => "elf32lriscv",
433 .riscv64 => "elf64lriscv",
434 .sparc => "elf32_sparc",
435 .sparc64 => "elf64_sparc",
436 .loongarch32 => "elf32loongarch",
437 .loongarch64 => "elf64loongarch",
438 .mips => "elf32btsmip",
439 .mipsel => "elf32ltsmip",
440 .mips64 => switch (target.abi) {
441 .gnuabin32, .muslabin32 => "elf32btsmipn32",
442 else => "elf64btsmip",
443 },
444 .mips64el => switch (target.abi) {
445 .gnuabin32, .muslabin32 => "elf32ltsmipn32",
446 else => "elf64ltsmip",
447 },
448 .x86_64 => switch (target.abi) {
449 .gnux32, .muslx32 => "elf32_x86_64",
450 else => "elf_x86_64",
451 },
452 .ve => "elf64ve",
453 .csky => "cskyelf_linux",
454 else => null,
455 };
456}
457
458pub fn get32BitArchVariant(target: std.Target) ?std.Target {
459 var copy = target;
460 switch (target.cpu.arch) {
461 .amdgcn,
462 .avr,
463 .msp430,
464 .spu_2,
465 .ve,
466 .bpfel,
467 .bpfeb,
468 .s390x,
469 => return null,
470
471 .arc,
472 .arm,
473 .armeb,
474 .csky,
475 .hexagon,
476 .m68k,
477 .mips,
478 .mipsel,
479 .powerpc,
480 .powerpcle,
481 .riscv32,
482 .sparc,
483 .thumb,
484 .thumbeb,
485 .x86,
486 .xcore,
487 .nvptx,
488 .kalimba,
489 .lanai,
490 .wasm32,
491 .spirv,
492 .spirv32,
493 .loongarch32,
494 .xtensa,
495 => {}, // Already 32 bit
496
497 .aarch64 => copy.cpu.arch = .arm,
498 .aarch64_be => copy.cpu.arch = .armeb,
499 .nvptx64 => copy.cpu.arch = .nvptx,
500 .wasm64 => copy.cpu.arch = .wasm32,
501 .spirv64 => copy.cpu.arch = .spirv32,
502 .loongarch64 => copy.cpu.arch = .loongarch32,
503 .mips64 => copy.cpu.arch = .mips,
504 .mips64el => copy.cpu.arch = .mipsel,
505 .powerpc64 => copy.cpu.arch = .powerpc,
506 .powerpc64le => copy.cpu.arch = .powerpcle,
507 .riscv64 => copy.cpu.arch = .riscv32,
508 .sparc64 => copy.cpu.arch = .sparc,
509 .x86_64 => copy.cpu.arch = .x86,
510 }
511 return copy;
512}
513
514pub fn get64BitArchVariant(target: std.Target) ?std.Target {
515 var copy = target;
516 switch (target.cpu.arch) {
517 .arc,
518 .avr,
519 .csky,
520 .hexagon,
521 .kalimba,
522 .lanai,
523 .m68k,
524 .msp430,
525 .spu_2,
526 .xcore,
527 .xtensa,
528 => return null,
529
530 .aarch64,
531 .aarch64_be,
532 .amdgcn,
533 .bpfeb,
534 .bpfel,
535 .nvptx64,
536 .wasm64,
537 .spirv64,
538 .loongarch64,
539 .mips64,
540 .mips64el,
541 .powerpc64,
542 .powerpc64le,
543 .riscv64,
544 .s390x,
545 .sparc64,
546 .ve,
547 .x86_64,
548 => {}, // Already 64 bit
549
550 .arm => copy.cpu.arch = .aarch64,
551 .armeb => copy.cpu.arch = .aarch64_be,
552 .loongarch32 => copy.cpu.arch = .loongarch64,
553 .mips => copy.cpu.arch = .mips64,
554 .mipsel => copy.cpu.arch = .mips64el,
555 .nvptx => copy.cpu.arch = .nvptx64,
556 .powerpc => copy.cpu.arch = .powerpc64,
557 .powerpcle => copy.cpu.arch = .powerpc64le,
558 .riscv32 => copy.cpu.arch = .riscv64,
559 .sparc => copy.cpu.arch = .sparc64,
560 .spirv => copy.cpu.arch = .spirv64,
561 .spirv32 => copy.cpu.arch = .spirv64,
562 .thumb => copy.cpu.arch = .aarch64,
563 .thumbeb => copy.cpu.arch = .aarch64_be,
564 .wasm32 => copy.cpu.arch = .wasm64,
565 .x86 => copy.cpu.arch = .x86_64,
566 }
567 return copy;
568}
569
570/// Adapted from Zig's src/codegen/llvm.zig
571pub fn toLLVMTriple(target: std.Target, buf: []u8) []const u8 {
572 // 64 bytes is assumed to be large enough to hold any target triple; increase if necessary
573 std.debug.assert(buf.len >= 64);
574
575 var stream = std.io.fixedBufferStream(buf);
576 const writer = stream.writer();
577
578 const llvm_arch = switch (target.cpu.arch) {
579 .arm => "arm",
580 .armeb => "armeb",
581 .aarch64 => if (target.abi == .ilp32) "aarch64_32" else "aarch64",
582 .aarch64_be => "aarch64_be",
583 .arc => "arc",
584 .avr => "avr",
585 .bpfel => "bpfel",
586 .bpfeb => "bpfeb",
587 .csky => "csky",
588 .hexagon => "hexagon",
589 .loongarch32 => "loongarch32",
590 .loongarch64 => "loongarch64",
591 .m68k => "m68k",
592 .mips => "mips",
593 .mipsel => "mipsel",
594 .mips64 => "mips64",
595 .mips64el => "mips64el",
596 .msp430 => "msp430",
597 .powerpc => "powerpc",
598 .powerpcle => "powerpcle",
599 .powerpc64 => "powerpc64",
600 .powerpc64le => "powerpc64le",
601 .amdgcn => "amdgcn",
602 .riscv32 => "riscv32",
603 .riscv64 => "riscv64",
604 .sparc => "sparc",
605 .sparc64 => "sparc64",
606 .s390x => "s390x",
607 .thumb => "thumb",
608 .thumbeb => "thumbeb",
609 .x86 => "i386",
610 .x86_64 => "x86_64",
611 .xcore => "xcore",
612 .xtensa => "xtensa",
613 .nvptx => "nvptx",
614 .nvptx64 => "nvptx64",
615 .spirv => "spirv",
616 .spirv32 => "spirv32",
617 .spirv64 => "spirv64",
618 .kalimba => "kalimba",
619 .lanai => "lanai",
620 .wasm32 => "wasm32",
621 .wasm64 => "wasm64",
622 .ve => "ve",
623 // Note: spu_2 is not supported in LLVM; this is the Zig arch name
624 .spu_2 => "spu_2",
625 };
626 writer.writeAll(llvm_arch) catch unreachable;
627 writer.writeByte('-') catch unreachable;
628
629 const llvm_os = switch (target.os.tag) {
630 .freestanding => "unknown",
631 .dragonfly => "dragonfly",
632 .freebsd => "freebsd",
633 .fuchsia => "fuchsia",
634 .linux => "linux",
635 .ps3 => "lv2",
636 .netbsd => "netbsd",
637 .openbsd => "openbsd",
638 .solaris => "solaris",
639 .illumos => "illumos",
640 .windows => "windows",
641 .zos => "zos",
642 .haiku => "haiku",
643 .rtems => "rtems",
644 .aix => "aix",
645 .cuda => "cuda",
646 .nvcl => "nvcl",
647 .amdhsa => "amdhsa",
648 .ps4 => "ps4",
649 .ps5 => "ps5",
650 .elfiamcu => "elfiamcu",
651 .mesa3d => "mesa3d",
652 .contiki => "contiki",
653 .amdpal => "amdpal",
654 .hermit => "hermit",
655 .hurd => "hurd",
656 .wasi => "wasi",
657 .emscripten => "emscripten",
658 .uefi => "windows",
659 .macos => "macosx",
660 .ios => "ios",
661 .tvos => "tvos",
662 .watchos => "watchos",
663 .driverkit => "driverkit",
664 .visionos => "xros",
665 .serenity => "serenity",
666 .opencl,
667 .opengl,
668 .vulkan,
669 .plan9,
670 .other,
671 => "unknown",
672 };
673 writer.writeAll(llvm_os) catch unreachable;
674
675 if (target.os.tag.isDarwin()) {
676 const min_version = target.os.version_range.semver.min;
677 writer.print("{d}.{d}.{d}", .{
678 min_version.major,
679 min_version.minor,
680 min_version.patch,
681 }) catch unreachable;
682 }
683 writer.writeByte('-') catch unreachable;
684
685 const llvm_abi = switch (target.abi) {
686 .none, .ilp32 => "unknown",
687 .gnu => "gnu",
688 .gnuabin32 => "gnuabin32",
689 .gnuabi64 => "gnuabi64",
690 .gnueabi => "gnueabi",
691 .gnueabihf => "gnueabihf",
692 .gnuf32 => "gnuf32",
693 .gnusf => "gnusf",
694 .gnux32 => "gnux32",
695 .gnuilp32 => "gnu_ilp32",
696 .code16 => "code16",
697 .eabi => "eabi",
698 .eabihf => "eabihf",
699 .android => "android",
700 .androideabi => "androideabi",
701 .musl => "musl",
702 .muslabin32 => "muslabin32",
703 .muslabi64 => "muslabi64",
704 .musleabi => "musleabi",
705 .musleabihf => "musleabihf",
706 .muslx32 => "muslx32",
707 .msvc => "msvc",
708 .itanium => "itanium",
709 .cygnus => "cygnus",
710 .simulator => "simulator",
711 .macabi => "macabi",
712 .ohos => "ohos",
713 .ohoseabi => "ohoseabi",
714 };
715 writer.writeAll(llvm_abi) catch unreachable;
716 return stream.getWritten();
717}
718
719test "alignment functions - smoke test" {
720 var target: std.Target = undefined;
721 const x86 = std.Target.Cpu.Arch.x86_64;
722 target.os = std.Target.Os.Tag.defaultVersionRange(.linux, x86, .none);
723 target.cpu = std.Target.Cpu.baseline(x86, target.os);
724 target.abi = std.Target.Abi.default(x86, target.os);
725
726 try std.testing.expect(isTlsSupported(target));
727 try std.testing.expect(!ignoreNonZeroSizedBitfieldTypeAlignment(target));
728 try std.testing.expect(minZeroWidthBitfieldAlignment(target) == null);
729 try std.testing.expect(!unnamedFieldAffectsAlignment(target));
730 try std.testing.expect(defaultAlignment(target) == 16);
731 try std.testing.expect(!packAllEnums(target));
732 try std.testing.expect(systemCompiler(target) == .gcc);
733
734 const arm = std.Target.Cpu.Arch.arm;
735 target.os = std.Target.Os.Tag.defaultVersionRange(.ios, arm, .none);
736 target.cpu = std.Target.Cpu.baseline(arm, target.os);
737 target.abi = std.Target.Abi.default(arm, target.os);
738
739 try std.testing.expect(!isTlsSupported(target));
740 try std.testing.expect(ignoreNonZeroSizedBitfieldTypeAlignment(target));
741 try std.testing.expectEqual(@as(?u29, 32), minZeroWidthBitfieldAlignment(target));
742 try std.testing.expect(unnamedFieldAffectsAlignment(target));
743 try std.testing.expect(defaultAlignment(target) == 16);
744 try std.testing.expect(!packAllEnums(target));
745 try std.testing.expect(systemCompiler(target) == .clang);
746}
747
748test "target size/align tests" {
749 var comp: @import("Compilation.zig") = undefined;
750
751 const x86 = std.Target.Cpu.Arch.x86;
752 comp.target.cpu.arch = x86;
753 comp.target.cpu.model = &std.Target.x86.cpu.i586;
754 comp.target.os = std.Target.Os.Tag.defaultVersionRange(.linux, x86, .none);
755 comp.target.abi = std.Target.Abi.gnu;
756
757 const tt: Type = .{
758 .specifier = .long_long,
759 };
760
761 try std.testing.expectEqual(@as(u64, 8), tt.sizeof(&comp).?);
762 try std.testing.expectEqual(@as(u64, 4), tt.alignof(&comp));
763
764 const arm = std.Target.Cpu.Arch.arm;
765 comp.target.cpu = std.Target.Cpu.Model.toCpu(&std.Target.arm.cpu.cortex_r4, arm);
766 comp.target.os = std.Target.Os.Tag.defaultVersionRange(.ios, arm, .none);
767 comp.target.abi = std.Target.Abi.none;
768
769 const ct: Type = .{
770 .specifier = .char,
771 };
772
773 try std.testing.expectEqual(true, std.Target.arm.featureSetHas(comp.target.cpu.features, .has_v7));
774 try std.testing.expectEqual(@as(u64, 1), ct.sizeof(&comp).?);
775 try std.testing.expectEqual(@as(u64, 1), ct.alignof(&comp));
776 try std.testing.expectEqual(true, ignoreNonZeroSizedBitfieldTypeAlignment(comp.target));
777}
778
779/// The canonical integer representation of nullptr_t.
780pub fn nullRepr(_: std.Target) u64 {
781 return 0;
782}
lib/compiler/aro/aro/text_literal.zig deleted-383
...@@ -1,383 +0,0 @@
1//! Parsing and classification of string and character literals
2
3const std = @import("std");
4const Compilation = @import("Compilation.zig");
5const Type = @import("Type.zig");
6const Diagnostics = @import("Diagnostics.zig");
7const Tokenizer = @import("Tokenizer.zig");
8const mem = std.mem;
9
10pub const Item = union(enum) {
11 /// decoded hex or character escape
12 value: u32,
13 /// validated unicode codepoint
14 codepoint: u21,
15 /// Char literal in the source text is not utf8 encoded
16 improperly_encoded: []const u8,
17 /// 1 or more unescaped bytes
18 utf8_text: std.unicode.Utf8View,
19};
20
21const CharDiagnostic = struct {
22 tag: Diagnostics.Tag,
23 extra: Diagnostics.Message.Extra,
24};
25
26pub const Kind = enum {
27 char,
28 wide,
29 utf_8,
30 utf_16,
31 utf_32,
32 /// Error kind that halts parsing
33 unterminated,
34
35 pub fn classify(id: Tokenizer.Token.Id, context: enum { string_literal, char_literal }) ?Kind {
36 return switch (context) {
37 .string_literal => switch (id) {
38 .string_literal => .char,
39 .string_literal_utf_8 => .utf_8,
40 .string_literal_wide => .wide,
41 .string_literal_utf_16 => .utf_16,
42 .string_literal_utf_32 => .utf_32,
43 .unterminated_string_literal => .unterminated,
44 else => null,
45 },
46 .char_literal => switch (id) {
47 .char_literal => .char,
48 .char_literal_utf_8 => .utf_8,
49 .char_literal_wide => .wide,
50 .char_literal_utf_16 => .utf_16,
51 .char_literal_utf_32 => .utf_32,
52 else => null,
53 },
54 };
55 }
56
57 /// Should only be called for string literals. Determines the result kind of two adjacent string
58 /// literals
59 pub fn concat(self: Kind, other: Kind) !Kind {
60 if (self == .unterminated or other == .unterminated) return .unterminated;
61 if (self == other) return self; // can always concat with own kind
62 if (self == .char) return other; // char + X -> X
63 if (other == .char) return self; // X + char -> X
64 return error.CannotConcat;
65 }
66
67 /// Largest unicode codepoint that can be represented by this character kind
68 /// May be smaller than the largest value that can be represented.
69 /// For example u8 char literals may only specify 0-127 via literals or
70 /// character escapes, but may specify up to \xFF via hex escapes.
71 pub fn maxCodepoint(kind: Kind, comp: *const Compilation) u21 {
72 return @intCast(switch (kind) {
73 .char => std.math.maxInt(u7),
74 .wide => @min(0x10FFFF, comp.wcharMax()),
75 .utf_8 => std.math.maxInt(u7),
76 .utf_16 => std.math.maxInt(u16),
77 .utf_32 => 0x10FFFF,
78 .unterminated => unreachable,
79 });
80 }
81
82 /// Largest integer that can be represented by this character kind
83 pub fn maxInt(kind: Kind, comp: *const Compilation) u32 {
84 return @intCast(switch (kind) {
85 .char, .utf_8 => std.math.maxInt(u8),
86 .wide => comp.wcharMax(),
87 .utf_16 => std.math.maxInt(u16),
88 .utf_32 => std.math.maxInt(u32),
89 .unterminated => unreachable,
90 });
91 }
92
93 /// The C type of a character literal of this kind
94 pub fn charLiteralType(kind: Kind, comp: *const Compilation) Type {
95 return switch (kind) {
96 .char => Type.int,
97 .wide => comp.types.wchar,
98 .utf_8 => .{ .specifier = .uchar },
99 .utf_16 => comp.types.uint_least16_t,
100 .utf_32 => comp.types.uint_least32_t,
101 .unterminated => unreachable,
102 };
103 }
104
105 /// Return the actual contents of the literal with leading / trailing quotes and
106 /// specifiers removed
107 pub fn contentSlice(kind: Kind, delimited: []const u8) []const u8 {
108 const end = delimited.len - 1; // remove trailing quote
109 return switch (kind) {
110 .char => delimited[1..end],
111 .wide => delimited[2..end],
112 .utf_8 => delimited[3..end],
113 .utf_16 => delimited[2..end],
114 .utf_32 => delimited[2..end],
115 .unterminated => unreachable,
116 };
117 }
118
119 /// The size of a character unit for a string literal of this kind
120 pub fn charUnitSize(kind: Kind, comp: *const Compilation) Compilation.CharUnitSize {
121 return switch (kind) {
122 .char => .@"1",
123 .wide => switch (comp.types.wchar.sizeof(comp).?) {
124 2 => .@"2",
125 4 => .@"4",
126 else => unreachable,
127 },
128 .utf_8 => .@"1",
129 .utf_16 => .@"2",
130 .utf_32 => .@"4",
131 .unterminated => unreachable,
132 };
133 }
134
135 /// Required alignment within aro (on compiler host) for writing to Interner.strings.
136 pub fn internalStorageAlignment(kind: Kind, comp: *const Compilation) usize {
137 return switch (kind.charUnitSize(comp)) {
138 inline else => |size| @alignOf(size.Type()),
139 };
140 }
141
142 /// The C type of an element of a string literal of this kind
143 pub fn elementType(kind: Kind, comp: *const Compilation) Type {
144 return switch (kind) {
145 .unterminated => unreachable,
146 .char => .{ .specifier = .char },
147 .utf_8 => if (comp.langopts.hasChar8_T()) .{ .specifier = .uchar } else .{ .specifier = .char },
148 else => kind.charLiteralType(comp),
149 };
150 }
151};
152
153pub const Parser = struct {
154 literal: []const u8,
155 i: usize = 0,
156 kind: Kind,
157 max_codepoint: u21,
158 /// We only want to issue a max of 1 error per char literal
159 errored: bool = false,
160 errors_buffer: [4]CharDiagnostic,
161 errors_len: usize,
162 comp: *const Compilation,
163
164 pub fn init(literal: []const u8, kind: Kind, max_codepoint: u21, comp: *const Compilation) Parser {
165 return .{
166 .literal = literal,
167 .comp = comp,
168 .kind = kind,
169 .max_codepoint = max_codepoint,
170 .errors_buffer = undefined,
171 .errors_len = 0,
172 };
173 }
174
175 fn prefixLen(self: *const Parser) usize {
176 return switch (self.kind) {
177 .unterminated => unreachable,
178 .char => 0,
179 .utf_8 => 2,
180 .wide, .utf_16, .utf_32 => 1,
181 };
182 }
183
184 pub fn errors(p: *Parser) []CharDiagnostic {
185 return p.errors_buffer[0..p.errors_len];
186 }
187
188 pub fn err(self: *Parser, tag: Diagnostics.Tag, extra: Diagnostics.Message.Extra) void {
189 if (self.errored) return;
190 self.errored = true;
191 const diagnostic: CharDiagnostic = .{ .tag = tag, .extra = extra };
192 if (self.errors_len == self.errors_buffer.len) {
193 self.errors_buffer[self.errors_buffer.len - 1] = diagnostic;
194 } else {
195 self.errors_buffer[self.errors_len] = diagnostic;
196 self.errors_len += 1;
197 }
198 }
199
200 pub fn warn(self: *Parser, tag: Diagnostics.Tag, extra: Diagnostics.Message.Extra) void {
201 if (self.errored) return;
202 if (self.errors_len < self.errors_buffer.len) {
203 self.errors_buffer[self.errors_len] = .{ .tag = tag, .extra = extra };
204 self.errors_len += 1;
205 }
206 }
207
208 pub fn next(self: *Parser) ?Item {
209 if (self.i >= self.literal.len) return null;
210
211 const start = self.i;
212 if (self.literal[start] != '\\') {
213 self.i = mem.indexOfScalarPos(u8, self.literal, start + 1, '\\') orelse self.literal.len;
214 const unescaped_slice = self.literal[start..self.i];
215
216 const view = std.unicode.Utf8View.init(unescaped_slice) catch {
217 if (self.kind != .char) {
218 self.err(.illegal_char_encoding_error, .{ .none = {} });
219 return null;
220 }
221 self.warn(.illegal_char_encoding_warning, .{ .none = {} });
222 return .{ .improperly_encoded = self.literal[start..self.i] };
223 };
224 return .{ .utf8_text = view };
225 }
226 switch (self.literal[start + 1]) {
227 'u', 'U' => return self.parseUnicodeEscape(),
228 else => return self.parseEscapedChar(),
229 }
230 }
231
232 fn parseUnicodeEscape(self: *Parser) ?Item {
233 const start = self.i;
234
235 std.debug.assert(self.literal[self.i] == '\\');
236
237 const kind = self.literal[self.i + 1];
238 std.debug.assert(kind == 'u' or kind == 'U');
239
240 self.i += 2;
241 if (self.i >= self.literal.len or !std.ascii.isHex(self.literal[self.i])) {
242 self.err(.missing_hex_escape, .{ .ascii = @intCast(kind) });
243 return null;
244 }
245 const expected_len: usize = if (kind == 'u') 4 else 8;
246 var overflowed = false;
247 var count: usize = 0;
248 var val: u32 = 0;
249
250 for (self.literal[self.i..], 0..) |c, i| {
251 if (i == expected_len) break;
252
253 const char = std.fmt.charToDigit(c, 16) catch {
254 break;
255 };
256
257 val, const overflow = @shlWithOverflow(val, 4);
258 overflowed = overflowed or overflow != 0;
259 val |= char;
260 count += 1;
261 }
262 self.i += expected_len;
263
264 if (overflowed) {
265 self.err(.escape_sequence_overflow, .{ .offset = start + self.prefixLen() });
266 return null;
267 }
268
269 if (count != expected_len) {
270 self.err(.incomplete_universal_character, .{ .none = {} });
271 return null;
272 }
273
274 if (val > std.math.maxInt(u21) or !std.unicode.utf8ValidCodepoint(@intCast(val))) {
275 self.err(.invalid_universal_character, .{ .offset = start + self.prefixLen() });
276 return null;
277 }
278
279 if (val > self.max_codepoint) {
280 self.err(.char_too_large, .{ .none = {} });
281 return null;
282 }
283
284 if (val < 0xA0 and (val != '$' and val != '@' and val != '`')) {
285 const is_error = !self.comp.langopts.standard.atLeast(.c23);
286 if (val >= 0x20 and val <= 0x7F) {
287 if (is_error) {
288 self.err(.ucn_basic_char_error, .{ .ascii = @intCast(val) });
289 } else {
290 self.warn(.ucn_basic_char_warning, .{ .ascii = @intCast(val) });
291 }
292 } else {
293 if (is_error) {
294 self.err(.ucn_control_char_error, .{ .none = {} });
295 } else {
296 self.warn(.ucn_control_char_warning, .{ .none = {} });
297 }
298 }
299 }
300
301 self.warn(.c89_ucn_in_literal, .{ .none = {} });
302 return .{ .codepoint = @intCast(val) };
303 }
304
305 fn parseEscapedChar(self: *Parser) Item {
306 self.i += 1;
307 const c = self.literal[self.i];
308 defer if (c != 'x' and (c < '0' or c > '7')) {
309 self.i += 1;
310 };
311
312 switch (c) {
313 '\n' => unreachable, // removed by line splicing
314 '\r' => unreachable, // removed by line splicing
315 '\'', '\"', '\\', '?' => return .{ .value = c },
316 'n' => return .{ .value = '\n' },
317 'r' => return .{ .value = '\r' },
318 't' => return .{ .value = '\t' },
319 'a' => return .{ .value = 0x07 },
320 'b' => return .{ .value = 0x08 },
321 'e', 'E' => {
322 self.warn(.non_standard_escape_char, .{ .invalid_escape = .{ .char = c, .offset = @intCast(self.i) } });
323 return .{ .value = 0x1B };
324 },
325 '(', '{', '[', '%' => {
326 self.warn(.non_standard_escape_char, .{ .invalid_escape = .{ .char = c, .offset = @intCast(self.i) } });
327 return .{ .value = c };
328 },
329 'f' => return .{ .value = 0x0C },
330 'v' => return .{ .value = 0x0B },
331 'x' => return .{ .value = self.parseNumberEscape(.hex) },
332 '0'...'7' => return .{ .value = self.parseNumberEscape(.octal) },
333 'u', 'U' => unreachable, // handled by parseUnicodeEscape
334 else => {
335 self.warn(.unknown_escape_sequence, .{ .invalid_escape = .{ .char = c, .offset = @intCast(self.i) } });
336 return .{ .value = c };
337 },
338 }
339 }
340
341 fn parseNumberEscape(self: *Parser, base: EscapeBase) u32 {
342 var val: u32 = 0;
343 var count: usize = 0;
344 var overflowed = false;
345 const start = self.i;
346 defer self.i += count;
347 const slice = switch (base) {
348 .octal => self.literal[self.i..@min(self.literal.len, self.i + 3)], // max 3 chars
349 .hex => blk: {
350 self.i += 1;
351 break :blk self.literal[self.i..]; // skip over 'x'; could have an arbitrary number of chars
352 },
353 };
354 for (slice) |c| {
355 const char = std.fmt.charToDigit(c, @intFromEnum(base)) catch break;
356 val, const overflow = @shlWithOverflow(val, base.log2());
357 if (overflow != 0) overflowed = true;
358 val += char;
359 count += 1;
360 }
361 if (overflowed or val > self.kind.maxInt(self.comp)) {
362 self.err(.escape_sequence_overflow, .{ .offset = start + self.prefixLen() });
363 return 0;
364 }
365 if (count == 0) {
366 std.debug.assert(base == .hex);
367 self.err(.missing_hex_escape, .{ .ascii = 'x' });
368 }
369 return val;
370 }
371};
372
373const EscapeBase = enum(u8) {
374 octal = 8,
375 hex = 16,
376
377 fn log2(base: EscapeBase) u4 {
378 return switch (base) {
379 .octal => 3,
380 .hex => 4,
381 };
382 }
383};
lib/compiler/aro/aro/toolchains/Linux.zig deleted-526
...@@ -1,526 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const Compilation = @import("../Compilation.zig");
4const GCCDetector = @import("../Driver/GCCDetector.zig");
5const Toolchain = @import("../Toolchain.zig");
6const Driver = @import("../Driver.zig");
7const Distro = @import("../Driver/Distro.zig");
8const target_util = @import("../target.zig");
9const system_defaults = @import("system_defaults");
10
11const Linux = @This();
12
13distro: Distro.Tag = .unknown,
14extra_opts: std.ArrayListUnmanaged([]const u8) = .empty,
15gcc_detector: GCCDetector = .{},
16
17pub fn discover(self: *Linux, tc: *Toolchain) !void {
18 self.distro = Distro.detect(tc.getTarget(), tc.filesystem);
19 try self.gcc_detector.discover(tc);
20 tc.selected_multilib = self.gcc_detector.selected;
21
22 try self.gcc_detector.appendToolPath(tc);
23 try self.buildExtraOpts(tc);
24 try self.findPaths(tc);
25}
26
27fn buildExtraOpts(self: *Linux, tc: *const Toolchain) !void {
28 const gpa = tc.driver.comp.gpa;
29 const target = tc.getTarget();
30 const is_android = target.isAndroid();
31 if (self.distro.isAlpine() or is_android) {
32 try self.extra_opts.ensureUnusedCapacity(gpa, 2);
33 self.extra_opts.appendAssumeCapacity("-z");
34 self.extra_opts.appendAssumeCapacity("now");
35 }
36
37 if (self.distro.isOpenSUSE() or self.distro.isUbuntu() or self.distro.isAlpine() or is_android) {
38 try self.extra_opts.ensureUnusedCapacity(gpa, 2);
39 self.extra_opts.appendAssumeCapacity("-z");
40 self.extra_opts.appendAssumeCapacity("relro");
41 }
42
43 if ((target.cpu.arch.isArm() and !target.cpu.arch.isThumb()) or target.cpu.arch.isAARCH64() or is_android) {
44 try self.extra_opts.ensureUnusedCapacity(gpa, 2);
45 self.extra_opts.appendAssumeCapacity("-z");
46 self.extra_opts.appendAssumeCapacity("max-page-size=4096");
47 }
48
49 if (target.cpu.arch == .arm or target.cpu.arch == .thumb) {
50 try self.extra_opts.append(gpa, "-X");
51 }
52
53 if (!target.cpu.arch.isMIPS() and target.cpu.arch != .hexagon) {
54 const hash_style = if (is_android) .both else self.distro.getHashStyle();
55 try self.extra_opts.append(gpa, switch (hash_style) {
56 inline else => |tag| "--hash-style=" ++ @tagName(tag),
57 });
58 }
59
60 if (system_defaults.enable_linker_build_id) {
61 try self.extra_opts.append(gpa, "--build-id");
62 }
63}
64
65fn addMultiLibPaths(self: *Linux, tc: *Toolchain, sysroot: []const u8, os_lib_dir: []const u8) !void {
66 if (!self.gcc_detector.is_valid) return;
67 const gcc_triple = self.gcc_detector.gcc_triple;
68 const lib_path = self.gcc_detector.parent_lib_path;
69
70 // Add lib/gcc/$triple/$version, with an optional /multilib suffix.
71 try tc.addPathIfExists(&.{ self.gcc_detector.install_path, tc.selected_multilib.gcc_suffix }, .file);
72
73 // Add lib/gcc/$triple/$libdir
74 // For GCC built with --enable-version-specific-runtime-libs.
75 try tc.addPathIfExists(&.{ self.gcc_detector.install_path, "..", os_lib_dir }, .file);
76
77 try tc.addPathIfExists(&.{ lib_path, "..", gcc_triple, "lib", "..", os_lib_dir, tc.selected_multilib.os_suffix }, .file);
78
79 // If the GCC installation we found is inside of the sysroot, we want to
80 // prefer libraries installed in the parent prefix of the GCC installation.
81 // It is important to *not* use these paths when the GCC installation is
82 // outside of the system root as that can pick up unintended libraries.
83 // This usually happens when there is an external cross compiler on the
84 // host system, and a more minimal sysroot available that is the target of
85 // the cross. Note that GCC does include some of these directories in some
86 // configurations but this seems somewhere between questionable and simply
87 // a bug.
88 if (mem.startsWith(u8, lib_path, sysroot)) {
89 try tc.addPathIfExists(&.{ lib_path, "..", os_lib_dir }, .file);
90 }
91}
92
93fn addMultiArchPaths(self: *Linux, tc: *Toolchain) !void {
94 if (!self.gcc_detector.is_valid) return;
95 const lib_path = self.gcc_detector.parent_lib_path;
96 const gcc_triple = self.gcc_detector.gcc_triple;
97 const multilib = self.gcc_detector.selected;
98 try tc.addPathIfExists(&.{ lib_path, "..", gcc_triple, "lib", multilib.os_suffix }, .file);
99}
100
101/// TODO: Very incomplete
102fn findPaths(self: *Linux, tc: *Toolchain) !void {
103 const target = tc.getTarget();
104 const sysroot = tc.getSysroot();
105
106 var output: [64]u8 = undefined;
107
108 const os_lib_dir = getOSLibDir(target);
109 const multiarch_triple = getMultiarchTriple(target) orelse target_util.toLLVMTriple(target, &output);
110
111 try self.addMultiLibPaths(tc, sysroot, os_lib_dir);
112
113 try tc.addPathIfExists(&.{ sysroot, "/lib", multiarch_triple }, .file);
114 try tc.addPathIfExists(&.{ sysroot, "/lib", "..", os_lib_dir }, .file);
115
116 if (target.isAndroid()) {
117 // TODO
118 }
119 try tc.addPathIfExists(&.{ sysroot, "/usr", "lib", multiarch_triple }, .file);
120 try tc.addPathIfExists(&.{ sysroot, "/usr", "lib", "..", os_lib_dir }, .file);
121
122 try self.addMultiArchPaths(tc);
123
124 try tc.addPathIfExists(&.{ sysroot, "/lib" }, .file);
125 try tc.addPathIfExists(&.{ sysroot, "/usr", "lib" }, .file);
126}
127
128pub fn deinit(self: *Linux, allocator: std.mem.Allocator) void {
129 self.extra_opts.deinit(allocator);
130}
131
132fn isPIEDefault(self: *const Linux) bool {
133 _ = self;
134 return false;
135}
136
137fn getPIE(self: *const Linux, d: *const Driver) bool {
138 if (d.shared or d.static or d.relocatable or d.static_pie) {
139 return false;
140 }
141 return d.pie orelse self.isPIEDefault();
142}
143
144fn getStaticPIE(self: *const Linux, d: *Driver) !bool {
145 _ = self;
146 if (d.static_pie and d.pie != null) {
147 try d.err("cannot specify 'nopie' along with 'static-pie'");
148 }
149 return d.static_pie;
150}
151
152fn getStatic(self: *const Linux, d: *const Driver) bool {
153 _ = self;
154 return d.static and !d.static_pie;
155}
156
157pub fn getDefaultLinker(self: *const Linux, target: std.Target) []const u8 {
158 _ = self;
159 if (target.isAndroid()) {
160 return "ld.lld";
161 }
162 return "ld";
163}
164
165pub fn buildLinkerArgs(self: *const Linux, tc: *const Toolchain, argv: *std.ArrayList([]const u8)) Compilation.Error!void {
166 const d = tc.driver;
167 const target = tc.getTarget();
168
169 const is_pie = self.getPIE(d);
170 const is_static_pie = try self.getStaticPIE(d);
171 const is_static = self.getStatic(d);
172 const is_android = target.isAndroid();
173 const is_iamcu = target.os.tag == .elfiamcu;
174 const is_ve = target.cpu.arch == .ve;
175 const has_crt_begin_end_files = target.abi != .none; // TODO: clang checks for MIPS vendor
176
177 if (is_pie) {
178 try argv.append("-pie");
179 }
180 if (is_static_pie) {
181 try argv.appendSlice(&.{ "-static", "-pie", "--no-dynamic-linker", "-z", "text" });
182 }
183
184 if (d.rdynamic) {
185 try argv.append("-export-dynamic");
186 }
187
188 if (d.strip) {
189 try argv.append("-s");
190 }
191
192 try argv.appendSlice(self.extra_opts.items);
193 try argv.append("--eh-frame-hdr");
194
195 // Todo: Driver should parse `-EL`/`-EB` for arm to set endianness for arm targets
196 if (target_util.ldEmulationOption(d.comp.target, null)) |emulation| {
197 try argv.appendSlice(&.{ "-m", emulation });
198 } else {
199 try d.err("Unknown target triple");
200 return;
201 }
202 if (d.comp.target.cpu.arch.isRISCV()) {
203 try argv.append("-X");
204 }
205 if (d.shared) {
206 try argv.append("-shared");
207 }
208 if (is_static) {
209 try argv.append("-static");
210 } else {
211 if (d.rdynamic) {
212 try argv.append("-export-dynamic");
213 }
214 if (!d.shared and !is_static_pie and !d.relocatable) {
215 const dynamic_linker = d.comp.target.standardDynamicLinkerPath();
216 // todo: check for --dyld-prefix
217 if (dynamic_linker.get()) |path| {
218 try argv.appendSlice(&.{ "-dynamic-linker", try tc.arena.dupe(u8, path) });
219 } else {
220 try d.err("Could not find dynamic linker path");
221 }
222 }
223 }
224
225 try argv.appendSlice(&.{ "-o", d.output_name orelse "a.out" });
226
227 if (!d.nostdlib and !d.nostartfiles and !d.relocatable) {
228 if (!is_android and !is_iamcu) {
229 if (!d.shared) {
230 const crt1 = if (is_pie)
231 "Scrt1.o"
232 else if (is_static_pie)
233 "rcrt1.o"
234 else
235 "crt1.o";
236 try argv.append(try tc.getFilePath(crt1));
237 }
238 try argv.append(try tc.getFilePath("crti.o"));
239 }
240 if (is_ve) {
241 try argv.appendSlice(&.{ "-z", "max-page-size=0x4000000" });
242 }
243
244 if (is_iamcu) {
245 try argv.append(try tc.getFilePath("crt0.o"));
246 } else if (has_crt_begin_end_files) {
247 var path: []const u8 = "";
248 if (tc.getRuntimeLibKind() == .compiler_rt and !is_android) {
249 const crt_begin = try tc.getCompilerRt("crtbegin", .object);
250 if (tc.filesystem.exists(crt_begin)) {
251 path = crt_begin;
252 }
253 }
254 if (path.len == 0) {
255 const crt_begin = if (tc.driver.shared)
256 if (is_android) "crtbegin_so.o" else "crtbeginS.o"
257 else if (is_static)
258 if (is_android) "crtbegin_static.o" else "crtbeginT.o"
259 else if (is_pie or is_static_pie)
260 if (is_android) "crtbegin_dynamic.o" else "crtbeginS.o"
261 else if (is_android) "crtbegin_dynamic.o" else "crtbegin.o";
262 path = try tc.getFilePath(crt_begin);
263 }
264 try argv.append(path);
265 }
266 }
267
268 // TODO add -L opts
269 // TODO add -u opts
270
271 try tc.addFilePathLibArgs(argv);
272
273 // TODO handle LTO
274
275 try argv.appendSlice(d.link_objects.items);
276
277 if (!d.nostdlib and !d.relocatable) {
278 if (!d.nodefaultlibs) {
279 if (is_static or is_static_pie) {
280 try argv.append("--start-group");
281 }
282 try tc.addRuntimeLibs(argv);
283
284 // TODO: add pthread if needed
285 if (!d.nolibc) {
286 try argv.append("-lc");
287 }
288 if (is_iamcu) {
289 try argv.append("-lgloss");
290 }
291 if (is_static or is_static_pie) {
292 try argv.append("--end-group");
293 } else {
294 try tc.addRuntimeLibs(argv);
295 }
296 if (is_iamcu) {
297 try argv.appendSlice(&.{ "--as-needed", "-lsoftfp", "--no-as-needed" });
298 }
299 }
300 if (!d.nostartfiles and !is_iamcu) {
301 if (has_crt_begin_end_files) {
302 var path: []const u8 = "";
303 if (tc.getRuntimeLibKind() == .compiler_rt and !is_android) {
304 const crt_end = try tc.getCompilerRt("crtend", .object);
305 if (tc.filesystem.exists(crt_end)) {
306 path = crt_end;
307 }
308 }
309 if (path.len == 0) {
310 const crt_end = if (d.shared)
311 if (is_android) "crtend_so.o" else "crtendS.o"
312 else if (is_pie or is_static_pie)
313 if (is_android) "crtend_android.o" else "crtendS.o"
314 else if (is_android) "crtend_android.o" else "crtend.o";
315 path = try tc.getFilePath(crt_end);
316 }
317 try argv.append(path);
318 }
319 if (!is_android) {
320 try argv.append(try tc.getFilePath("crtn.o"));
321 }
322 }
323 }
324
325 // TODO add -T args
326}
327
328fn getMultiarchTriple(target: std.Target) ?[]const u8 {
329 const is_android = target.isAndroid();
330 const is_mips_r6 = std.Target.mips.featureSetHas(target.cpu.features, .mips32r6);
331 return switch (target.cpu.arch) {
332 .arm, .thumb => if (is_android) "arm-linux-androideabi" else if (target.abi == .gnueabihf) "arm-linux-gnueabihf" else "arm-linux-gnueabi",
333 .armeb, .thumbeb => if (target.abi == .gnueabihf) "armeb-linux-gnueabihf" else "armeb-linux-gnueabi",
334 .aarch64 => if (is_android) "aarch64-linux-android" else "aarch64-linux-gnu",
335 .aarch64_be => "aarch64_be-linux-gnu",
336 .x86 => if (is_android) "i686-linux-android" else "i386-linux-gnu",
337 .x86_64 => if (is_android) "x86_64-linux-android" else if (target.abi == .gnux32) "x86_64-linux-gnux32" else "x86_64-linux-gnu",
338 .m68k => "m68k-linux-gnu",
339 .mips => if (is_mips_r6) "mipsisa32r6-linux-gnu" else "mips-linux-gnu",
340 .mipsel => if (is_android) "mipsel-linux-android" else if (is_mips_r6) "mipsisa32r6el-linux-gnu" else "mipsel-linux-gnu",
341 .powerpcle => "powerpcle-linux-gnu",
342 .powerpc64 => "powerpc64-linux-gnu",
343 .powerpc64le => "powerpc64le-linux-gnu",
344 .riscv64 => "riscv64-linux-gnu",
345 .sparc => "sparc-linux-gnu",
346 .sparc64 => "sparc64-linux-gnu",
347 .s390x => "s390x-linux-gnu",
348
349 // TODO: expand this
350 else => null,
351 };
352}
353
354fn getOSLibDir(target: std.Target) []const u8 {
355 switch (target.cpu.arch) {
356 .x86,
357 .powerpc,
358 .powerpcle,
359 .sparc,
360 => return "lib32",
361 else => {},
362 }
363 if (target.cpu.arch == .x86_64 and (target.abi == .gnux32 or target.abi == .muslx32)) {
364 return "libx32";
365 }
366 if (target.cpu.arch == .riscv32) {
367 return "lib32";
368 }
369 if (target.ptrBitWidth() == 32) {
370 return "lib";
371 }
372 return "lib64";
373}
374
375pub fn defineSystemIncludes(self: *const Linux, tc: *const Toolchain) !void {
376 if (tc.driver.nostdinc) return;
377
378 const comp = tc.driver.comp;
379 const target = tc.getTarget();
380
381 // musl prefers /usr/include before builtin includes, so musl targets will add builtins
382 // at the end of this function (unless disabled with nostdlibinc)
383 if (!tc.driver.nobuiltininc and (!target.isMusl() or tc.driver.nostdlibinc)) {
384 try comp.addBuiltinIncludeDir(tc.driver.aro_name);
385 }
386
387 if (tc.driver.nostdlibinc) return;
388
389 const sysroot = tc.getSysroot();
390 const local_include = try std.fmt.allocPrint(comp.gpa, "{s}{s}", .{ sysroot, "/usr/local/include" });
391 defer comp.gpa.free(local_include);
392 try comp.addSystemIncludeDir(local_include);
393
394 if (self.gcc_detector.is_valid) {
395 const gcc_include_path = try std.fs.path.join(comp.gpa, &.{ self.gcc_detector.parent_lib_path, "..", self.gcc_detector.gcc_triple, "include" });
396 defer comp.gpa.free(gcc_include_path);
397 try comp.addSystemIncludeDir(gcc_include_path);
398 }
399
400 if (getMultiarchTriple(target)) |triple| {
401 const joined = try std.fs.path.join(comp.gpa, &.{ sysroot, "usr", "include", triple });
402 defer comp.gpa.free(joined);
403 if (tc.filesystem.exists(joined)) {
404 try comp.addSystemIncludeDir(joined);
405 }
406 }
407
408 if (target.os.tag == .rtems) return;
409
410 try comp.addSystemIncludeDir("/include");
411 try comp.addSystemIncludeDir("/usr/include");
412
413 std.debug.assert(!tc.driver.nostdlibinc);
414 if (!tc.driver.nobuiltininc and target.isMusl()) {
415 try comp.addBuiltinIncludeDir(tc.driver.aro_name);
416 }
417}
418
419test Linux {
420 if (@import("builtin").os.tag == .windows) return error.SkipZigTest;
421
422 var arena_instance = std.heap.ArenaAllocator.init(std.testing.allocator);
423 defer arena_instance.deinit();
424 const arena = arena_instance.allocator();
425
426 var comp = Compilation.init(std.testing.allocator, std.fs.cwd());
427 defer comp.deinit();
428 comp.environment = .{
429 .path = "/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin",
430 };
431 defer comp.environment = .{};
432
433 const raw_triple = "x86_64-linux-gnu";
434 const target_query = try std.Target.Query.parse(.{ .arch_os_abi = raw_triple });
435 comp.target = try std.zig.system.resolveTargetQuery(target_query);
436 comp.langopts.setEmulatedCompiler(.gcc);
437
438 var driver: Driver = .{ .comp = &comp };
439 defer driver.deinit();
440 driver.raw_target_triple = raw_triple;
441
442 const link_obj = try driver.comp.gpa.dupe(u8, "/tmp/foo.o");
443 try driver.link_objects.append(driver.comp.gpa, link_obj);
444 driver.temp_file_count += 1;
445
446 var toolchain: Toolchain = .{ .driver = &driver, .arena = arena, .filesystem = .{ .fake = &.{
447 .{ .path = "/tmp" },
448 .{ .path = "/usr" },
449 .{ .path = "/usr/lib64" },
450 .{ .path = "/usr/bin" },
451 .{ .path = "/usr/bin/ld", .executable = true },
452 .{ .path = "/lib" },
453 .{ .path = "/lib/x86_64-linux-gnu" },
454 .{ .path = "/lib/x86_64-linux-gnu/crt1.o" },
455 .{ .path = "/lib/x86_64-linux-gnu/crti.o" },
456 .{ .path = "/lib/x86_64-linux-gnu/crtn.o" },
457 .{ .path = "/lib64" },
458 .{ .path = "/usr/lib" },
459 .{ .path = "/usr/lib/gcc" },
460 .{ .path = "/usr/lib/gcc/x86_64-linux-gnu" },
461 .{ .path = "/usr/lib/gcc/x86_64-linux-gnu/9" },
462 .{ .path = "/usr/lib/gcc/x86_64-linux-gnu/9/crtbegin.o" },
463 .{ .path = "/usr/lib/gcc/x86_64-linux-gnu/9/crtend.o" },
464 .{ .path = "/usr/lib/x86_64-linux-gnu" },
465 .{ .path = "/etc/lsb-release", .contents =
466 \\DISTRIB_ID=Ubuntu
467 \\DISTRIB_RELEASE=20.04
468 \\DISTRIB_CODENAME=focal
469 \\DISTRIB_DESCRIPTION="Ubuntu 20.04.6 LTS"
470 \\
471 },
472 } } };
473 defer toolchain.deinit();
474
475 try toolchain.discover();
476
477 var argv = std.ArrayList([]const u8).init(driver.comp.gpa);
478 defer argv.deinit();
479
480 var linker_path_buf: [std.fs.max_path_bytes]u8 = undefined;
481 const linker_path = try toolchain.getLinkerPath(&linker_path_buf);
482 try argv.append(linker_path);
483
484 try toolchain.buildLinkerArgs(&argv);
485
486 const expected = [_][]const u8{
487 "/usr/bin/ld",
488 "-z",
489 "relro",
490 "--hash-style=gnu",
491 "--eh-frame-hdr",
492 "-m",
493 "elf_x86_64",
494 "-dynamic-linker",
495 "/lib64/ld-linux-x86-64.so.2",
496 "-o",
497 "a.out",
498 "/lib/x86_64-linux-gnu/crt1.o",
499 "/lib/x86_64-linux-gnu/crti.o",
500 "/usr/lib/gcc/x86_64-linux-gnu/9/crtbegin.o",
501 "-L/usr/lib/gcc/x86_64-linux-gnu/9",
502 "-L/usr/lib/gcc/x86_64-linux-gnu/9/../../../../lib64",
503 "-L/lib/x86_64-linux-gnu",
504 "-L/lib/../lib64",
505 "-L/usr/lib/x86_64-linux-gnu",
506 "-L/usr/lib/../lib64",
507 "-L/lib",
508 "-L/usr/lib",
509 link_obj,
510 "-lgcc",
511 "--as-needed",
512 "-lgcc_s",
513 "--no-as-needed",
514 "-lc",
515 "-lgcc",
516 "--as-needed",
517 "-lgcc_s",
518 "--no-as-needed",
519 "/usr/lib/gcc/x86_64-linux-gnu/9/crtend.o",
520 "/lib/x86_64-linux-gnu/crtn.o",
521 };
522 try std.testing.expectEqual(expected.len, argv.items.len);
523 for (expected, argv.items) |expected_item, actual_item| {
524 try std.testing.expectEqualStrings(expected_item, actual_item);
525 }
526}
lib/compiler/aro/aro/tracy.zig deleted-310
...@@ -1,310 +0,0 @@
1//! Copied from https://github.com/ziglang/zig/blob/c9006d9479c619d9ed555164831e11a04d88d382/src/tracy.zig
2
3const std = @import("std");
4const builtin = @import("builtin");
5const build_options = @import("build_options");
6
7pub const enable = if (builtin.is_test) false else build_options.enable_tracy;
8pub const enable_allocation = enable and build_options.enable_tracy_allocation;
9pub const enable_callstack = enable and build_options.enable_tracy_callstack;
10
11// TODO: make this configurable
12const callstack_depth = 10;
13
14const ___tracy_c_zone_context = extern struct {
15 id: u32,
16 active: c_int,
17
18 pub inline fn end(self: @This()) void {
19 ___tracy_emit_zone_end(self);
20 }
21
22 pub inline fn addText(self: @This(), text: []const u8) void {
23 ___tracy_emit_zone_text(self, text.ptr, text.len);
24 }
25
26 pub inline fn setName(self: @This(), name: []const u8) void {
27 ___tracy_emit_zone_name(self, name.ptr, name.len);
28 }
29
30 pub inline fn setColor(self: @This(), color: u32) void {
31 ___tracy_emit_zone_color(self, color);
32 }
33
34 pub inline fn setValue(self: @This(), value: u64) void {
35 ___tracy_emit_zone_value(self, value);
36 }
37};
38
39pub const Ctx = if (enable) ___tracy_c_zone_context else struct {
40 pub inline fn end(self: @This()) void {
41 _ = self;
42 }
43
44 pub inline fn addText(self: @This(), text: []const u8) void {
45 _ = self;
46 _ = text;
47 }
48
49 pub inline fn setName(self: @This(), name: []const u8) void {
50 _ = self;
51 _ = name;
52 }
53
54 pub inline fn setColor(self: @This(), color: u32) void {
55 _ = self;
56 _ = color;
57 }
58
59 pub inline fn setValue(self: @This(), value: u64) void {
60 _ = self;
61 _ = value;
62 }
63};
64
65pub inline fn trace(comptime src: std.builtin.SourceLocation) Ctx {
66 if (!enable) return .{};
67
68 if (enable_callstack) {
69 return ___tracy_emit_zone_begin_callstack(&.{
70 .name = null,
71 .function = src.fn_name.ptr,
72 .file = src.file.ptr,
73 .line = src.line,
74 .color = 0,
75 }, callstack_depth, 1);
76 } else {
77 return ___tracy_emit_zone_begin(&.{
78 .name = null,
79 .function = src.fn_name.ptr,
80 .file = src.file.ptr,
81 .line = src.line,
82 .color = 0,
83 }, 1);
84 }
85}
86
87pub inline fn traceNamed(comptime src: std.builtin.SourceLocation, comptime name: [:0]const u8) Ctx {
88 if (!enable) return .{};
89
90 if (enable_callstack) {
91 return ___tracy_emit_zone_begin_callstack(&.{
92 .name = name.ptr,
93 .function = src.fn_name.ptr,
94 .file = src.file.ptr,
95 .line = src.line,
96 .color = 0,
97 }, callstack_depth, 1);
98 } else {
99 return ___tracy_emit_zone_begin(&.{
100 .name = name.ptr,
101 .function = src.fn_name.ptr,
102 .file = src.file.ptr,
103 .line = src.line,
104 .color = 0,
105 }, 1);
106 }
107}
108
109pub fn tracyAllocator(allocator: std.mem.Allocator) TracyAllocator(null) {
110 return TracyAllocator(null).init(allocator);
111}
112
113pub fn TracyAllocator(comptime name: ?[:0]const u8) type {
114 return struct {
115 parent_allocator: std.mem.Allocator,
116
117 const Self = @This();
118
119 pub fn init(parent_allocator: std.mem.Allocator) Self {
120 return .{
121 .parent_allocator = parent_allocator,
122 };
123 }
124
125 pub fn allocator(self: *Self) std.mem.Allocator {
126 return std.mem.Allocator.init(self, allocFn, resizeFn, freeFn);
127 }
128
129 fn allocFn(self: *Self, len: usize, ptr_align: u29, len_align: u29, ret_addr: usize) std.mem.Allocator.Error![]u8 {
130 const result = self.parent_allocator.rawAlloc(len, ptr_align, len_align, ret_addr);
131 if (result) |data| {
132 if (data.len != 0) {
133 if (name) |n| {
134 allocNamed(data.ptr, data.len, n);
135 } else {
136 alloc(data.ptr, data.len);
137 }
138 }
139 } else |_| {
140 messageColor("allocation failed", 0xFF0000);
141 }
142 return result;
143 }
144
145 fn resizeFn(self: *Self, buf: []u8, buf_align: u29, new_len: usize, len_align: u29, ret_addr: usize) ?usize {
146 if (self.parent_allocator.rawResize(buf, buf_align, new_len, len_align, ret_addr)) |resized_len| {
147 if (name) |n| {
148 freeNamed(buf.ptr, n);
149 allocNamed(buf.ptr, resized_len, n);
150 } else {
151 free(buf.ptr);
152 alloc(buf.ptr, resized_len);
153 }
154
155 return resized_len;
156 }
157
158 // during normal operation the compiler hits this case thousands of times due to this
159 // emitting messages for it is both slow and causes clutter
160 return null;
161 }
162
163 fn freeFn(self: *Self, buf: []u8, buf_align: u29, ret_addr: usize) void {
164 self.parent_allocator.rawFree(buf, buf_align, ret_addr);
165 // this condition is to handle free being called on an empty slice that was never even allocated
166 // example case: `std.process.getSelfExeSharedLibPaths` can return `&[_][:0]u8{}`
167 if (buf.len != 0) {
168 if (name) |n| {
169 freeNamed(buf.ptr, n);
170 } else {
171 free(buf.ptr);
172 }
173 }
174 }
175 };
176}
177
178// This function only accepts comptime known strings, see `messageCopy` for runtime strings
179pub inline fn message(comptime msg: [:0]const u8) void {
180 if (!enable) return;
181 ___tracy_emit_messageL(msg.ptr, if (enable_callstack) callstack_depth else 0);
182}
183
184// This function only accepts comptime known strings, see `messageColorCopy` for runtime strings
185pub inline fn messageColor(comptime msg: [:0]const u8, color: u32) void {
186 if (!enable) return;
187 ___tracy_emit_messageLC(msg.ptr, color, if (enable_callstack) callstack_depth else 0);
188}
189
190pub inline fn messageCopy(msg: []const u8) void {
191 if (!enable) return;
192 ___tracy_emit_message(msg.ptr, msg.len, if (enable_callstack) callstack_depth else 0);
193}
194
195pub inline fn messageColorCopy(msg: [:0]const u8, color: u32) void {
196 if (!enable) return;
197 ___tracy_emit_messageC(msg.ptr, msg.len, color, if (enable_callstack) callstack_depth else 0);
198}
199
200pub inline fn frameMark() void {
201 if (!enable) return;
202 ___tracy_emit_frame_mark(null);
203}
204
205pub inline fn frameMarkNamed(comptime name: [:0]const u8) void {
206 if (!enable) return;
207 ___tracy_emit_frame_mark(name.ptr);
208}
209
210pub inline fn namedFrame(comptime name: [:0]const u8) Frame(name) {
211 frameMarkStart(name);
212 return .{};
213}
214
215pub fn Frame(comptime name: [:0]const u8) type {
216 return struct {
217 pub fn end(_: @This()) void {
218 frameMarkEnd(name);
219 }
220 };
221}
222
223inline fn frameMarkStart(comptime name: [:0]const u8) void {
224 if (!enable) return;
225 ___tracy_emit_frame_mark_start(name.ptr);
226}
227
228inline fn frameMarkEnd(comptime name: [:0]const u8) void {
229 if (!enable) return;
230 ___tracy_emit_frame_mark_end(name.ptr);
231}
232
233extern fn ___tracy_emit_frame_mark_start(name: [*:0]const u8) void;
234extern fn ___tracy_emit_frame_mark_end(name: [*:0]const u8) void;
235
236inline fn alloc(ptr: [*]u8, len: usize) void {
237 if (!enable) return;
238
239 if (enable_callstack) {
240 ___tracy_emit_memory_alloc_callstack(ptr, len, callstack_depth, 0);
241 } else {
242 ___tracy_emit_memory_alloc(ptr, len, 0);
243 }
244}
245
246inline fn allocNamed(ptr: [*]u8, len: usize, comptime name: [:0]const u8) void {
247 if (!enable) return;
248
249 if (enable_callstack) {
250 ___tracy_emit_memory_alloc_callstack_named(ptr, len, callstack_depth, 0, name.ptr);
251 } else {
252 ___tracy_emit_memory_alloc_named(ptr, len, 0, name.ptr);
253 }
254}
255
256inline fn free(ptr: [*]u8) void {
257 if (!enable) return;
258
259 if (enable_callstack) {
260 ___tracy_emit_memory_free_callstack(ptr, callstack_depth, 0);
261 } else {
262 ___tracy_emit_memory_free(ptr, 0);
263 }
264}
265
266inline fn freeNamed(ptr: [*]u8, comptime name: [:0]const u8) void {
267 if (!enable) return;
268
269 if (enable_callstack) {
270 ___tracy_emit_memory_free_callstack_named(ptr, callstack_depth, 0, name.ptr);
271 } else {
272 ___tracy_emit_memory_free_named(ptr, 0, name.ptr);
273 }
274}
275
276extern fn ___tracy_emit_zone_begin(
277 srcloc: *const ___tracy_source_location_data,
278 active: c_int,
279) ___tracy_c_zone_context;
280extern fn ___tracy_emit_zone_begin_callstack(
281 srcloc: *const ___tracy_source_location_data,
282 depth: c_int,
283 active: c_int,
284) ___tracy_c_zone_context;
285extern fn ___tracy_emit_zone_text(ctx: ___tracy_c_zone_context, txt: [*]const u8, size: usize) void;
286extern fn ___tracy_emit_zone_name(ctx: ___tracy_c_zone_context, txt: [*]const u8, size: usize) void;
287extern fn ___tracy_emit_zone_color(ctx: ___tracy_c_zone_context, color: u32) void;
288extern fn ___tracy_emit_zone_value(ctx: ___tracy_c_zone_context, value: u64) void;
289extern fn ___tracy_emit_zone_end(ctx: ___tracy_c_zone_context) void;
290extern fn ___tracy_emit_memory_alloc(ptr: *const anyopaque, size: usize, secure: c_int) void;
291extern fn ___tracy_emit_memory_alloc_callstack(ptr: *const anyopaque, size: usize, depth: c_int, secure: c_int) void;
292extern fn ___tracy_emit_memory_free(ptr: *const anyopaque, secure: c_int) void;
293extern fn ___tracy_emit_memory_free_callstack(ptr: *const anyopaque, depth: c_int, secure: c_int) void;
294extern fn ___tracy_emit_memory_alloc_named(ptr: *const anyopaque, size: usize, secure: c_int, name: [*:0]const u8) void;
295extern fn ___tracy_emit_memory_alloc_callstack_named(ptr: *const anyopaque, size: usize, depth: c_int, secure: c_int, name: [*:0]const u8) void;
296extern fn ___tracy_emit_memory_free_named(ptr: *const anyopaque, secure: c_int, name: [*:0]const u8) void;
297extern fn ___tracy_emit_memory_free_callstack_named(ptr: *const anyopaque, depth: c_int, secure: c_int, name: [*:0]const u8) void;
298extern fn ___tracy_emit_message(txt: [*]const u8, size: usize, callstack: c_int) void;
299extern fn ___tracy_emit_messageL(txt: [*:0]const u8, callstack: c_int) void;
300extern fn ___tracy_emit_messageC(txt: [*]const u8, size: usize, color: u32, callstack: c_int) void;
301extern fn ___tracy_emit_messageLC(txt: [*:0]const u8, color: u32, callstack: c_int) void;
302extern fn ___tracy_emit_frame_mark(name: ?[*:0]const u8) void;
303
304const ___tracy_source_location_data = extern struct {
305 name: ?[*:0]const u8,
306 function: [*:0]const u8,
307 file: [*:0]const u8,
308 line: u32,
309 color: u32,
310};
lib/compiler/aro/backend.zig deleted-13
...@@ -1,13 +0,0 @@
1pub const Interner = @import("backend/Interner.zig");
2pub const Ir = @import("backend/Ir.zig");
3pub const Object = @import("backend/Object.zig");
4
5pub const CallingConvention = enum {
6 C,
7 stdcall,
8 thiscall,
9 vectorcall,
10};
11
12pub const version_str = "aro-zig";
13pub const version = @import("std").SemanticVersion.parse(version_str) catch unreachable;
lib/compiler/aro/backend/Interner.zig deleted-873
...@@ -1,873 +0,0 @@
1const std = @import("std");
2const Allocator = std.mem.Allocator;
3const assert = std.debug.assert;
4const BigIntConst = std.math.big.int.Const;
5const BigIntMutable = std.math.big.int.Mutable;
6const Hash = std.hash.Wyhash;
7const Limb = std.math.big.Limb;
8
9const Interner = @This();
10
11map: std.AutoArrayHashMapUnmanaged(void, void) = .empty,
12items: std.MultiArrayList(struct {
13 tag: Tag,
14 data: u32,
15}) = .{},
16extra: std.ArrayListUnmanaged(u32) = .empty,
17limbs: std.ArrayListUnmanaged(Limb) = .empty,
18strings: std.ArrayListUnmanaged(u8) = .empty,
19
20const KeyAdapter = struct {
21 interner: *const Interner,
22
23 pub fn eql(adapter: KeyAdapter, a: Key, b_void: void, b_map_index: usize) bool {
24 _ = b_void;
25 return adapter.interner.get(@as(Ref, @enumFromInt(b_map_index))).eql(a);
26 }
27
28 pub fn hash(adapter: KeyAdapter, a: Key) u32 {
29 _ = adapter;
30 return a.hash();
31 }
32};
33
34pub const Key = union(enum) {
35 int_ty: u16,
36 float_ty: u16,
37 complex_ty: u16,
38 ptr_ty,
39 noreturn_ty,
40 void_ty,
41 func_ty,
42 array_ty: struct {
43 len: u64,
44 child: Ref,
45 },
46 vector_ty: struct {
47 len: u32,
48 child: Ref,
49 },
50 record_ty: []const Ref,
51 /// May not be zero
52 null,
53 int: union(enum) {
54 u64: u64,
55 i64: i64,
56 big_int: BigIntConst,
57
58 pub fn toBigInt(repr: @This(), space: *Tag.Int.BigIntSpace) BigIntConst {
59 return switch (repr) {
60 .big_int => |x| x,
61 inline .u64, .i64 => |x| BigIntMutable.init(&space.limbs, x).toConst(),
62 };
63 }
64 },
65 float: Float,
66 complex: Complex,
67 bytes: []const u8,
68
69 pub const Float = union(enum) {
70 f16: f16,
71 f32: f32,
72 f64: f64,
73 f80: f80,
74 f128: f128,
75 };
76 pub const Complex = union(enum) {
77 cf16: [2]f16,
78 cf32: [2]f32,
79 cf64: [2]f64,
80 cf80: [2]f80,
81 cf128: [2]f128,
82 };
83
84 pub fn hash(key: Key) u32 {
85 var hasher = Hash.init(0);
86 const tag = std.meta.activeTag(key);
87 std.hash.autoHash(&hasher, tag);
88 switch (key) {
89 .bytes => |bytes| {
90 hasher.update(bytes);
91 },
92 .record_ty => |elems| for (elems) |elem| {
93 std.hash.autoHash(&hasher, elem);
94 },
95 .float => |repr| switch (repr) {
96 inline else => |data| std.hash.autoHash(
97 &hasher,
98 @as(std.meta.Int(.unsigned, @bitSizeOf(@TypeOf(data))), @bitCast(data)),
99 ),
100 },
101 .complex => |repr| switch (repr) {
102 inline else => |data| std.hash.autoHash(
103 &hasher,
104 @as(std.meta.Int(.unsigned, @bitSizeOf(@TypeOf(data))), @bitCast(data)),
105 ),
106 },
107 .int => |repr| {
108 var space: Tag.Int.BigIntSpace = undefined;
109 const big = repr.toBigInt(&space);
110 std.hash.autoHash(&hasher, big.positive);
111 for (big.limbs) |limb| std.hash.autoHash(&hasher, limb);
112 },
113 inline else => |info| {
114 std.hash.autoHash(&hasher, info);
115 },
116 }
117 return @truncate(hasher.final());
118 }
119
120 pub fn eql(a: Key, b: Key) bool {
121 const KeyTag = std.meta.Tag(Key);
122 const a_tag: KeyTag = a;
123 const b_tag: KeyTag = b;
124 if (a_tag != b_tag) return false;
125 switch (a) {
126 .record_ty => |a_elems| {
127 const b_elems = b.record_ty;
128 if (a_elems.len != b_elems.len) return false;
129 for (a_elems, b_elems) |a_elem, b_elem| {
130 if (a_elem != b_elem) return false;
131 }
132 return true;
133 },
134 .bytes => |a_bytes| {
135 const b_bytes = b.bytes;
136 return std.mem.eql(u8, a_bytes, b_bytes);
137 },
138 .int => |a_repr| {
139 var a_space: Tag.Int.BigIntSpace = undefined;
140 const a_big = a_repr.toBigInt(&a_space);
141 var b_space: Tag.Int.BigIntSpace = undefined;
142 const b_big = b.int.toBigInt(&b_space);
143
144 return a_big.eql(b_big);
145 },
146 inline else => |a_info, tag| {
147 const b_info = @field(b, @tagName(tag));
148 return std.meta.eql(a_info, b_info);
149 },
150 }
151 }
152
153 fn toRef(key: Key) ?Ref {
154 switch (key) {
155 .int_ty => |bits| switch (bits) {
156 1 => return .i1,
157 8 => return .i8,
158 16 => return .i16,
159 32 => return .i32,
160 64 => return .i64,
161 128 => return .i128,
162 else => {},
163 },
164 .float_ty => |bits| switch (bits) {
165 16 => return .f16,
166 32 => return .f32,
167 64 => return .f64,
168 80 => return .f80,
169 128 => return .f128,
170 else => unreachable,
171 },
172 .complex_ty => |bits| switch (bits) {
173 16 => return .cf16,
174 32 => return .cf32,
175 64 => return .cf64,
176 80 => return .cf80,
177 128 => return .cf128,
178 else => unreachable,
179 },
180 .ptr_ty => return .ptr,
181 .func_ty => return .func,
182 .noreturn_ty => return .noreturn,
183 .void_ty => return .void,
184 .int => |repr| {
185 var space: Tag.Int.BigIntSpace = undefined;
186 const big = repr.toBigInt(&space);
187 if (big.eqlZero()) return .zero;
188 const big_one = BigIntConst{ .limbs = &.{1}, .positive = true };
189 if (big.eql(big_one)) return .one;
190 },
191 .float => |repr| switch (repr) {
192 inline else => |data| {
193 if (std.math.isPositiveZero(data)) return .zero;
194 if (data == 1) return .one;
195 },
196 },
197 .null => return .null,
198 else => {},
199 }
200 return null;
201 }
202};
203
204pub const Ref = enum(u32) {
205 const max = std.math.maxInt(u32);
206
207 ptr = max - 1,
208 noreturn = max - 2,
209 void = max - 3,
210 i1 = max - 4,
211 i8 = max - 5,
212 i16 = max - 6,
213 i32 = max - 7,
214 i64 = max - 8,
215 i128 = max - 9,
216 f16 = max - 10,
217 f32 = max - 11,
218 f64 = max - 12,
219 f80 = max - 13,
220 f128 = max - 14,
221 func = max - 15,
222 zero = max - 16,
223 one = max - 17,
224 null = max - 18,
225 cf16 = max - 19,
226 cf32 = max - 20,
227 cf64 = max - 21,
228 cf80 = max - 22,
229 cf128 = max - 23,
230 _,
231};
232
233pub const OptRef = enum(u32) {
234 const max = std.math.maxInt(u32);
235
236 none = max - 0,
237 ptr = max - 1,
238 noreturn = max - 2,
239 void = max - 3,
240 i1 = max - 4,
241 i8 = max - 5,
242 i16 = max - 6,
243 i32 = max - 7,
244 i64 = max - 8,
245 i128 = max - 9,
246 f16 = max - 10,
247 f32 = max - 11,
248 f64 = max - 12,
249 f80 = max - 13,
250 f128 = max - 14,
251 func = max - 15,
252 zero = max - 16,
253 one = max - 17,
254 null = max - 18,
255 cf16 = max - 19,
256 cf32 = max - 20,
257 cf64 = max - 21,
258 cf80 = max - 22,
259 cf128 = max - 23,
260 _,
261};
262
263pub const Tag = enum(u8) {
264 /// `data` is `u16`
265 int_ty,
266 /// `data` is `u16`
267 float_ty,
268 /// `data` is `u16`
269 complex_ty,
270 /// `data` is index to `Array`
271 array_ty,
272 /// `data` is index to `Vector`
273 vector_ty,
274 /// `data` is `u32`
275 u32,
276 /// `data` is `i32`
277 i32,
278 /// `data` is `Int`
279 int_positive,
280 /// `data` is `Int`
281 int_negative,
282 /// `data` is `f16`
283 f16,
284 /// `data` is `f32`
285 f32,
286 /// `data` is `F64`
287 f64,
288 /// `data` is `F80`
289 f80,
290 /// `data` is `F128`
291 f128,
292 /// `data` is `CF16`
293 cf16,
294 /// `data` is `CF32`
295 cf32,
296 /// `data` is `CF64`
297 cf64,
298 /// `data` is `CF80`
299 cf80,
300 /// `data` is `CF128`
301 cf128,
302 /// `data` is `Bytes`
303 bytes,
304 /// `data` is `Record`
305 record_ty,
306
307 pub const Array = struct {
308 len0: u32,
309 len1: u32,
310 child: Ref,
311
312 pub fn getLen(a: Array) u64 {
313 return (PackedU64{
314 .a = a.len0,
315 .b = a.len1,
316 }).get();
317 }
318 };
319
320 pub const Vector = struct {
321 len: u32,
322 child: Ref,
323 };
324
325 pub const Int = struct {
326 limbs_index: u32,
327 limbs_len: u32,
328
329 /// Big enough to fit any non-BigInt value
330 pub const BigIntSpace = struct {
331 /// The +1 is headroom so that operations such as incrementing once
332 /// or decrementing once are possible without using an allocator.
333 limbs: [(@sizeOf(u64) / @sizeOf(std.math.big.Limb)) + 1]std.math.big.Limb,
334 };
335 };
336
337 pub const F64 = struct {
338 piece0: u32,
339 piece1: u32,
340
341 pub fn get(self: F64) f64 {
342 const int_bits = @as(u64, self.piece0) | (@as(u64, self.piece1) << 32);
343 return @bitCast(int_bits);
344 }
345
346 fn pack(val: f64) F64 {
347 const bits = @as(u64, @bitCast(val));
348 return .{
349 .piece0 = @as(u32, @truncate(bits)),
350 .piece1 = @as(u32, @truncate(bits >> 32)),
351 };
352 }
353 };
354
355 pub const F80 = struct {
356 piece0: u32,
357 piece1: u32,
358 piece2: u32, // u16 part, top bits
359
360 pub fn get(self: F80) f80 {
361 const int_bits = @as(u80, self.piece0) |
362 (@as(u80, self.piece1) << 32) |
363 (@as(u80, self.piece2) << 64);
364 return @bitCast(int_bits);
365 }
366
367 fn pack(val: f80) F80 {
368 const bits = @as(u80, @bitCast(val));
369 return .{
370 .piece0 = @as(u32, @truncate(bits)),
371 .piece1 = @as(u32, @truncate(bits >> 32)),
372 .piece2 = @as(u16, @truncate(bits >> 64)),
373 };
374 }
375 };
376
377 pub const F128 = struct {
378 piece0: u32,
379 piece1: u32,
380 piece2: u32,
381 piece3: u32,
382
383 pub fn get(self: F128) f128 {
384 const int_bits = @as(u128, self.piece0) |
385 (@as(u128, self.piece1) << 32) |
386 (@as(u128, self.piece2) << 64) |
387 (@as(u128, self.piece3) << 96);
388 return @bitCast(int_bits);
389 }
390
391 fn pack(val: f128) F128 {
392 const bits = @as(u128, @bitCast(val));
393 return .{
394 .piece0 = @as(u32, @truncate(bits)),
395 .piece1 = @as(u32, @truncate(bits >> 32)),
396 .piece2 = @as(u32, @truncate(bits >> 64)),
397 .piece3 = @as(u32, @truncate(bits >> 96)),
398 };
399 }
400 };
401
402 pub const CF16 = struct {
403 piece0: u32,
404
405 pub fn get(self: CF16) [2]f16 {
406 const real: f16 = @bitCast(@as(u16, @truncate(self.piece0 >> 16)));
407 const imag: f16 = @bitCast(@as(u16, @truncate(self.piece0)));
408 return .{
409 real,
410 imag,
411 };
412 }
413
414 fn pack(val: [2]f16) CF16 {
415 const real: u16 = @bitCast(val[0]);
416 const imag: u16 = @bitCast(val[1]);
417 return .{
418 .piece0 = (@as(u32, real) << 16) | @as(u32, imag),
419 };
420 }
421 };
422
423 pub const CF32 = struct {
424 piece0: u32,
425 piece1: u32,
426
427 pub fn get(self: CF32) [2]f32 {
428 return .{
429 @bitCast(self.piece0),
430 @bitCast(self.piece1),
431 };
432 }
433
434 fn pack(val: [2]f32) CF32 {
435 return .{
436 .piece0 = @bitCast(val[0]),
437 .piece1 = @bitCast(val[1]),
438 };
439 }
440 };
441
442 pub const CF64 = struct {
443 piece0: u32,
444 piece1: u32,
445 piece2: u32,
446 piece3: u32,
447
448 pub fn get(self: CF64) [2]f64 {
449 return .{
450 (F64{ .piece0 = self.piece0, .piece1 = self.piece1 }).get(),
451 (F64{ .piece0 = self.piece2, .piece1 = self.piece3 }).get(),
452 };
453 }
454
455 fn pack(val: [2]f64) CF64 {
456 const real = F64.pack(val[0]);
457 const imag = F64.pack(val[1]);
458 return .{
459 .piece0 = real.piece0,
460 .piece1 = real.piece1,
461 .piece2 = imag.piece0,
462 .piece3 = imag.piece1,
463 };
464 }
465 };
466
467 /// TODO pack into 5 pieces
468 pub const CF80 = struct {
469 piece0: u32,
470 piece1: u32,
471 piece2: u32, // u16 part, top bits
472 piece3: u32,
473 piece4: u32,
474 piece5: u32, // u16 part, top bits
475
476 pub fn get(self: CF80) [2]f80 {
477 return .{
478 (F80{ .piece0 = self.piece0, .piece1 = self.piece1, .piece2 = self.piece2 }).get(),
479 (F80{ .piece0 = self.piece3, .piece1 = self.piece4, .piece2 = self.piece5 }).get(),
480 };
481 }
482
483 fn pack(val: [2]f80) CF80 {
484 const real = F80.pack(val[0]);
485 const imag = F80.pack(val[1]);
486 return .{
487 .piece0 = real.piece0,
488 .piece1 = real.piece1,
489 .piece2 = real.piece2,
490 .piece3 = imag.piece0,
491 .piece4 = imag.piece1,
492 .piece5 = imag.piece2,
493 };
494 }
495 };
496
497 pub const CF128 = struct {
498 piece0: u32,
499 piece1: u32,
500 piece2: u32,
501 piece3: u32,
502 piece4: u32,
503 piece5: u32,
504 piece6: u32,
505 piece7: u32,
506
507 pub fn get(self: CF128) [2]f128 {
508 return .{
509 (F128{ .piece0 = self.piece0, .piece1 = self.piece1, .piece2 = self.piece2, .piece3 = self.piece3 }).get(),
510 (F128{ .piece0 = self.piece4, .piece1 = self.piece5, .piece2 = self.piece6, .piece3 = self.piece7 }).get(),
511 };
512 }
513
514 fn pack(val: [2]f128) CF128 {
515 const real = F128.pack(val[0]);
516 const imag = F128.pack(val[1]);
517 return .{
518 .piece0 = real.piece0,
519 .piece1 = real.piece1,
520 .piece2 = real.piece2,
521 .piece3 = real.piece3,
522 .piece4 = imag.piece0,
523 .piece5 = imag.piece1,
524 .piece6 = imag.piece2,
525 .piece7 = imag.piece3,
526 };
527 }
528 };
529
530 pub const Bytes = struct {
531 strings_index: u32,
532 len: u32,
533 };
534
535 pub const Record = struct {
536 elements_len: u32,
537 // trailing
538 // [elements_len]Ref
539 };
540};
541
542pub const PackedU64 = packed struct(u64) {
543 a: u32,
544 b: u32,
545
546 pub fn get(x: PackedU64) u64 {
547 return @bitCast(x);
548 }
549
550 pub fn init(x: u64) PackedU64 {
551 return @bitCast(x);
552 }
553};
554
555pub fn deinit(i: *Interner, gpa: Allocator) void {
556 i.map.deinit(gpa);
557 i.items.deinit(gpa);
558 i.extra.deinit(gpa);
559 i.limbs.deinit(gpa);
560 i.strings.deinit(gpa);
561}
562
563pub fn put(i: *Interner, gpa: Allocator, key: Key) !Ref {
564 if (key.toRef()) |some| return some;
565 const adapter: KeyAdapter = .{ .interner = i };
566 const gop = try i.map.getOrPutAdapted(gpa, key, adapter);
567 if (gop.found_existing) return @enumFromInt(gop.index);
568 try i.items.ensureUnusedCapacity(gpa, 1);
569
570 switch (key) {
571 .int_ty => |bits| {
572 i.items.appendAssumeCapacity(.{
573 .tag = .int_ty,
574 .data = bits,
575 });
576 },
577 .float_ty => |bits| {
578 i.items.appendAssumeCapacity(.{
579 .tag = .float_ty,
580 .data = bits,
581 });
582 },
583 .complex_ty => |bits| {
584 i.items.appendAssumeCapacity(.{
585 .tag = .complex_ty,
586 .data = bits,
587 });
588 },
589 .array_ty => |info| {
590 const split_len = PackedU64.init(info.len);
591 i.items.appendAssumeCapacity(.{
592 .tag = .array_ty,
593 .data = try i.addExtra(gpa, Tag.Array{
594 .len0 = split_len.a,
595 .len1 = split_len.b,
596 .child = info.child,
597 }),
598 });
599 },
600 .vector_ty => |info| {
601 i.items.appendAssumeCapacity(.{
602 .tag = .vector_ty,
603 .data = try i.addExtra(gpa, Tag.Vector{
604 .len = info.len,
605 .child = info.child,
606 }),
607 });
608 },
609 .int => |repr| int: {
610 var space: Tag.Int.BigIntSpace = undefined;
611 const big = repr.toBigInt(&space);
612 switch (repr) {
613 .u64 => |data| if (std.math.cast(u32, data)) |small| {
614 i.items.appendAssumeCapacity(.{
615 .tag = .u32,
616 .data = small,
617 });
618 break :int;
619 },
620 .i64 => |data| if (std.math.cast(i32, data)) |small| {
621 i.items.appendAssumeCapacity(.{
622 .tag = .i32,
623 .data = @bitCast(small),
624 });
625 break :int;
626 },
627 .big_int => |data| {
628 if (data.fitsInTwosComp(.unsigned, 32)) {
629 i.items.appendAssumeCapacity(.{
630 .tag = .u32,
631 .data = data.to(u32) catch unreachable,
632 });
633 break :int;
634 } else if (data.fitsInTwosComp(.signed, 32)) {
635 i.items.appendAssumeCapacity(.{
636 .tag = .i32,
637 .data = @bitCast(data.to(i32) catch unreachable),
638 });
639 break :int;
640 }
641 },
642 }
643 const limbs_index: u32 = @intCast(i.limbs.items.len);
644 try i.limbs.appendSlice(gpa, big.limbs);
645 i.items.appendAssumeCapacity(.{
646 .tag = if (big.positive) .int_positive else .int_negative,
647 .data = try i.addExtra(gpa, Tag.Int{
648 .limbs_index = limbs_index,
649 .limbs_len = @intCast(big.limbs.len),
650 }),
651 });
652 },
653 .float => |repr| switch (repr) {
654 .f16 => |data| i.items.appendAssumeCapacity(.{
655 .tag = .f16,
656 .data = @as(u16, @bitCast(data)),
657 }),
658 .f32 => |data| i.items.appendAssumeCapacity(.{
659 .tag = .f32,
660 .data = @as(u32, @bitCast(data)),
661 }),
662 .f64 => |data| i.items.appendAssumeCapacity(.{
663 .tag = .f64,
664 .data = try i.addExtra(gpa, Tag.F64.pack(data)),
665 }),
666 .f80 => |data| i.items.appendAssumeCapacity(.{
667 .tag = .f80,
668 .data = try i.addExtra(gpa, Tag.F80.pack(data)),
669 }),
670 .f128 => |data| i.items.appendAssumeCapacity(.{
671 .tag = .f128,
672 .data = try i.addExtra(gpa, Tag.F128.pack(data)),
673 }),
674 },
675 .complex => |repr| switch (repr) {
676 .cf16 => |data| i.items.appendAssumeCapacity(.{
677 .tag = .cf16,
678 .data = try i.addExtra(gpa, Tag.CF16.pack(data)),
679 }),
680 .cf32 => |data| i.items.appendAssumeCapacity(.{
681 .tag = .cf32,
682 .data = try i.addExtra(gpa, Tag.CF32.pack(data)),
683 }),
684 .cf64 => |data| i.items.appendAssumeCapacity(.{
685 .tag = .cf64,
686 .data = try i.addExtra(gpa, Tag.CF64.pack(data)),
687 }),
688 .cf80 => |data| i.items.appendAssumeCapacity(.{
689 .tag = .cf80,
690 .data = try i.addExtra(gpa, Tag.CF80.pack(data)),
691 }),
692 .cf128 => |data| i.items.appendAssumeCapacity(.{
693 .tag = .cf128,
694 .data = try i.addExtra(gpa, Tag.CF128.pack(data)),
695 }),
696 },
697 .bytes => |bytes| {
698 const strings_index: u32 = @intCast(i.strings.items.len);
699 try i.strings.appendSlice(gpa, bytes);
700 i.items.appendAssumeCapacity(.{
701 .tag = .bytes,
702 .data = try i.addExtra(gpa, Tag.Bytes{
703 .strings_index = strings_index,
704 .len = @intCast(bytes.len),
705 }),
706 });
707 },
708 .record_ty => |elems| {
709 try i.extra.ensureUnusedCapacity(gpa, @typeInfo(Tag.Record).@"struct".fields.len +
710 elems.len);
711 i.items.appendAssumeCapacity(.{
712 .tag = .record_ty,
713 .data = i.addExtraAssumeCapacity(Tag.Record{
714 .elements_len = @intCast(elems.len),
715 }),
716 });
717 i.extra.appendSliceAssumeCapacity(@ptrCast(elems));
718 },
719 .ptr_ty,
720 .noreturn_ty,
721 .void_ty,
722 .func_ty,
723 .null,
724 => unreachable,
725 }
726
727 return @enumFromInt(gop.index);
728}
729
730fn addExtra(i: *Interner, gpa: Allocator, extra: anytype) Allocator.Error!u32 {
731 const fields = @typeInfo(@TypeOf(extra)).@"struct".fields;
732 try i.extra.ensureUnusedCapacity(gpa, fields.len);
733 return i.addExtraAssumeCapacity(extra);
734}
735
736fn addExtraAssumeCapacity(i: *Interner, extra: anytype) u32 {
737 const result = @as(u32, @intCast(i.extra.items.len));
738 inline for (@typeInfo(@TypeOf(extra)).@"struct".fields) |field| {
739 i.extra.appendAssumeCapacity(switch (field.type) {
740 Ref => @intFromEnum(@field(extra, field.name)),
741 u32 => @field(extra, field.name),
742 else => @compileError("bad field type: " ++ @typeName(field.type)),
743 });
744 }
745 return result;
746}
747
748pub fn get(i: *const Interner, ref: Ref) Key {
749 switch (ref) {
750 .ptr => return .ptr_ty,
751 .func => return .func_ty,
752 .noreturn => return .noreturn_ty,
753 .void => return .void_ty,
754 .i1 => return .{ .int_ty = 1 },
755 .i8 => return .{ .int_ty = 8 },
756 .i16 => return .{ .int_ty = 16 },
757 .i32 => return .{ .int_ty = 32 },
758 .i64 => return .{ .int_ty = 64 },
759 .i128 => return .{ .int_ty = 128 },
760 .f16 => return .{ .float_ty = 16 },
761 .f32 => return .{ .float_ty = 32 },
762 .f64 => return .{ .float_ty = 64 },
763 .f80 => return .{ .float_ty = 80 },
764 .f128 => return .{ .float_ty = 128 },
765 .zero => return .{ .int = .{ .u64 = 0 } },
766 .one => return .{ .int = .{ .u64 = 1 } },
767 .null => return .null,
768 .cf16 => return .{ .complex_ty = 16 },
769 .cf32 => return .{ .complex_ty = 32 },
770 .cf64 => return .{ .complex_ty = 64 },
771 .cf80 => return .{ .complex_ty = 80 },
772 else => {},
773 }
774
775 const item = i.items.get(@intFromEnum(ref));
776 const data = item.data;
777 return switch (item.tag) {
778 .int_ty => .{ .int_ty = @intCast(data) },
779 .float_ty => .{ .float_ty = @intCast(data) },
780 .complex_ty => .{ .complex_ty = @intCast(data) },
781 .array_ty => {
782 const array_ty = i.extraData(Tag.Array, data);
783 return .{ .array_ty = .{
784 .len = array_ty.getLen(),
785 .child = array_ty.child,
786 } };
787 },
788 .vector_ty => {
789 const vector_ty = i.extraData(Tag.Vector, data);
790 return .{ .vector_ty = .{
791 .len = vector_ty.len,
792 .child = vector_ty.child,
793 } };
794 },
795 .u32 => .{ .int = .{ .u64 = data } },
796 .i32 => .{ .int = .{ .i64 = @as(i32, @bitCast(data)) } },
797 .int_positive, .int_negative => {
798 const int_info = i.extraData(Tag.Int, data);
799 const limbs = i.limbs.items[int_info.limbs_index..][0..int_info.limbs_len];
800 return .{ .int = .{
801 .big_int = .{
802 .positive = item.tag == .int_positive,
803 .limbs = limbs,
804 },
805 } };
806 },
807 .f16 => .{ .float = .{ .f16 = @bitCast(@as(u16, @intCast(data))) } },
808 .f32 => .{ .float = .{ .f32 = @bitCast(data) } },
809 .f64 => {
810 const float = i.extraData(Tag.F64, data);
811 return .{ .float = .{ .f64 = float.get() } };
812 },
813 .f80 => {
814 const float = i.extraData(Tag.F80, data);
815 return .{ .float = .{ .f80 = float.get() } };
816 },
817 .f128 => {
818 const float = i.extraData(Tag.F128, data);
819 return .{ .float = .{ .f128 = float.get() } };
820 },
821 .cf16 => {
822 const components = i.extraData(Tag.CF16, data);
823 return .{ .complex = .{ .cf16 = components.get() } };
824 },
825 .cf32 => {
826 const components = i.extraData(Tag.CF32, data);
827 return .{ .complex = .{ .cf32 = components.get() } };
828 },
829 .cf64 => {
830 const components = i.extraData(Tag.CF64, data);
831 return .{ .complex = .{ .cf64 = components.get() } };
832 },
833 .cf80 => {
834 const components = i.extraData(Tag.CF80, data);
835 return .{ .complex = .{ .cf80 = components.get() } };
836 },
837 .cf128 => {
838 const components = i.extraData(Tag.CF128, data);
839 return .{ .complex = .{ .cf128 = components.get() } };
840 },
841 .bytes => {
842 const bytes = i.extraData(Tag.Bytes, data);
843 return .{ .bytes = i.strings.items[bytes.strings_index..][0..bytes.len] };
844 },
845 .record_ty => {
846 const extra = i.extraDataTrail(Tag.Record, data);
847 return .{
848 .record_ty = @ptrCast(i.extra.items[extra.end..][0..extra.data.elements_len]),
849 };
850 },
851 };
852}
853
854fn extraData(i: *const Interner, comptime T: type, index: usize) T {
855 return i.extraDataTrail(T, index).data;
856}
857
858fn extraDataTrail(i: *const Interner, comptime T: type, index: usize) struct { data: T, end: u32 } {
859 var result: T = undefined;
860 const fields = @typeInfo(T).@"struct".fields;
861 inline for (fields, 0..) |field, field_i| {
862 const int32 = i.extra.items[field_i + index];
863 @field(result, field.name) = switch (field.type) {
864 Ref => @enumFromInt(int32),
865 u32 => int32,
866 else => @compileError("bad field type: " ++ @typeName(field.type)),
867 };
868 }
869 return .{
870 .data = result,
871 .end = @intCast(index + fields.len),
872 };
873}
lib/compiler/aro/backend/Ir.zig deleted-697
...@@ -1,697 +0,0 @@
1const std = @import("std");
2const Allocator = std.mem.Allocator;
3const assert = std.debug.assert;
4const Interner = @import("Interner.zig");
5const Object = @import("Object.zig");
6
7const Ir = @This();
8
9interner: *Interner,
10decls: std.StringArrayHashMapUnmanaged(Decl),
11
12pub const Decl = struct {
13 instructions: std.MultiArrayList(Inst),
14 body: std.ArrayListUnmanaged(Ref),
15 arena: std.heap.ArenaAllocator.State,
16
17 pub fn deinit(decl: *Decl, gpa: Allocator) void {
18 decl.instructions.deinit(gpa);
19 decl.body.deinit(gpa);
20 decl.arena.promote(gpa).deinit();
21 }
22};
23
24pub const Builder = struct {
25 gpa: Allocator,
26 arena: std.heap.ArenaAllocator,
27 interner: *Interner,
28
29 decls: std.StringArrayHashMapUnmanaged(Decl) = .empty,
30 instructions: std.MultiArrayList(Ir.Inst) = .{},
31 body: std.ArrayListUnmanaged(Ref) = .empty,
32 alloc_count: u32 = 0,
33 arg_count: u32 = 0,
34 current_label: Ref = undefined,
35
36 pub fn deinit(b: *Builder) void {
37 for (b.decls.values()) |*decl| {
38 decl.deinit(b.gpa);
39 }
40 b.decls.deinit(b.gpa);
41 b.arena.deinit();
42 b.instructions.deinit(b.gpa);
43 b.body.deinit(b.gpa);
44 b.* = undefined;
45 }
46
47 pub fn finish(b: *Builder) Ir {
48 return .{
49 .interner = b.interner,
50 .decls = b.decls.move(),
51 };
52 }
53
54 pub fn startFn(b: *Builder) Allocator.Error!void {
55 const entry = try b.makeLabel("entry");
56 try b.body.append(b.gpa, entry);
57 b.current_label = entry;
58 }
59
60 pub fn finishFn(b: *Builder, name: []const u8) !void {
61 var duped_instructions = try b.instructions.clone(b.gpa);
62 errdefer duped_instructions.deinit(b.gpa);
63 var duped_body = try b.body.clone(b.gpa);
64 errdefer duped_body.deinit(b.gpa);
65
66 try b.decls.put(b.gpa, name, .{
67 .instructions = duped_instructions,
68 .body = duped_body,
69 .arena = b.arena.state,
70 });
71 b.instructions.shrinkRetainingCapacity(0);
72 b.body.shrinkRetainingCapacity(0);
73 b.arena = std.heap.ArenaAllocator.init(b.gpa);
74 b.alloc_count = 0;
75 b.arg_count = 0;
76 }
77
78 pub fn startBlock(b: *Builder, label: Ref) !void {
79 try b.body.append(b.gpa, label);
80 b.current_label = label;
81 }
82
83 pub fn addArg(b: *Builder, ty: Interner.Ref) Allocator.Error!Ref {
84 const ref: Ref = @enumFromInt(b.instructions.len);
85 try b.instructions.append(b.gpa, .{ .tag = .arg, .data = .{ .none = {} }, .ty = ty });
86 try b.body.insert(b.gpa, b.arg_count, ref);
87 b.arg_count += 1;
88 return ref;
89 }
90
91 pub fn addAlloc(b: *Builder, size: u32, @"align": u32) Allocator.Error!Ref {
92 const ref: Ref = @enumFromInt(b.instructions.len);
93 try b.instructions.append(b.gpa, .{
94 .tag = .alloc,
95 .data = .{ .alloc = .{ .size = size, .@"align" = @"align" } },
96 .ty = .ptr,
97 });
98 try b.body.insert(b.gpa, b.alloc_count + b.arg_count + 1, ref);
99 b.alloc_count += 1;
100 return ref;
101 }
102
103 pub fn addInst(b: *Builder, tag: Ir.Inst.Tag, data: Ir.Inst.Data, ty: Interner.Ref) Allocator.Error!Ref {
104 const ref: Ref = @enumFromInt(b.instructions.len);
105 try b.instructions.append(b.gpa, .{ .tag = tag, .data = data, .ty = ty });
106 try b.body.append(b.gpa, ref);
107 return ref;
108 }
109
110 pub fn makeLabel(b: *Builder, name: [*:0]const u8) Allocator.Error!Ref {
111 const ref: Ref = @enumFromInt(b.instructions.len);
112 try b.instructions.append(b.gpa, .{ .tag = .label, .data = .{ .label = name }, .ty = .void });
113 return ref;
114 }
115
116 pub fn addJump(b: *Builder, label: Ref) Allocator.Error!void {
117 _ = try b.addInst(.jmp, .{ .un = label }, .noreturn);
118 }
119
120 pub fn addBranch(b: *Builder, cond: Ref, true_label: Ref, false_label: Ref) Allocator.Error!void {
121 const branch = try b.arena.allocator().create(Ir.Inst.Branch);
122 branch.* = .{
123 .cond = cond,
124 .then = true_label,
125 .@"else" = false_label,
126 };
127 _ = try b.addInst(.branch, .{ .branch = branch }, .noreturn);
128 }
129
130 pub fn addSwitch(b: *Builder, target: Ref, values: []Interner.Ref, labels: []Ref, default: Ref) Allocator.Error!void {
131 assert(values.len == labels.len);
132 const a = b.arena.allocator();
133 const @"switch" = try a.create(Ir.Inst.Switch);
134 @"switch".* = .{
135 .target = target,
136 .cases_len = @intCast(values.len),
137 .case_vals = (try a.dupe(Interner.Ref, values)).ptr,
138 .case_labels = (try a.dupe(Ref, labels)).ptr,
139 .default = default,
140 };
141 _ = try b.addInst(.@"switch", .{ .@"switch" = @"switch" }, .noreturn);
142 }
143
144 pub fn addStore(b: *Builder, ptr: Ref, val: Ref) Allocator.Error!void {
145 _ = try b.addInst(.store, .{ .bin = .{ .lhs = ptr, .rhs = val } }, .void);
146 }
147
148 pub fn addConstant(b: *Builder, val: Interner.Ref, ty: Interner.Ref) Allocator.Error!Ref {
149 const ref: Ref = @enumFromInt(b.instructions.len);
150 try b.instructions.append(b.gpa, .{
151 .tag = .constant,
152 .data = .{ .constant = val },
153 .ty = ty,
154 });
155 return ref;
156 }
157
158 pub fn addPhi(b: *Builder, inputs: []const Inst.Phi.Input, ty: Interner.Ref) Allocator.Error!Ref {
159 const a = b.arena.allocator();
160 const input_refs = try a.alloc(Ref, inputs.len * 2 + 1);
161 input_refs[0] = @enumFromInt(inputs.len);
162 @memcpy(input_refs[1..], std.mem.bytesAsSlice(Ref, std.mem.sliceAsBytes(inputs)));
163
164 return b.addInst(.phi, .{ .phi = .{ .ptr = input_refs.ptr } }, ty);
165 }
166
167 pub fn addSelect(b: *Builder, cond: Ref, then: Ref, @"else": Ref, ty: Interner.Ref) Allocator.Error!Ref {
168 const branch = try b.arena.allocator().create(Ir.Inst.Branch);
169 branch.* = .{
170 .cond = cond,
171 .then = then,
172 .@"else" = @"else",
173 };
174 return b.addInst(.select, .{ .branch = branch }, ty);
175 }
176};
177
178pub const Renderer = struct {
179 gpa: Allocator,
180 obj: *Object,
181 ir: *const Ir,
182 errors: ErrorList = .{},
183
184 pub const ErrorList = std.StringArrayHashMapUnmanaged([]const u8);
185
186 pub const Error = Allocator.Error || error{LowerFail};
187
188 pub fn deinit(r: *Renderer) void {
189 for (r.errors.values()) |msg| r.gpa.free(msg);
190 r.errors.deinit(r.gpa);
191 }
192
193 pub fn render(r: *Renderer) !void {
194 switch (r.obj.target.cpu.arch) {
195 .x86, .x86_64 => return @import("Ir/x86/Renderer.zig").render(r),
196 else => unreachable,
197 }
198 }
199
200 pub fn fail(
201 r: *Renderer,
202 name: []const u8,
203 comptime format: []const u8,
204 args: anytype,
205 ) Error {
206 try r.errors.ensureUnusedCapacity(r.gpa, 1);
207 r.errors.putAssumeCapacity(name, try std.fmt.allocPrint(r.gpa, format, args));
208 return error.LowerFail;
209 }
210};
211
212pub fn render(
213 ir: *const Ir,
214 gpa: Allocator,
215 target: std.Target,
216 errors: ?*Renderer.ErrorList,
217) !*Object {
218 const obj = try Object.create(gpa, target);
219 errdefer obj.deinit();
220
221 var renderer: Renderer = .{
222 .gpa = gpa,
223 .obj = obj,
224 .ir = ir,
225 };
226 defer {
227 if (errors) |some| {
228 some.* = renderer.errors.move();
229 }
230 renderer.deinit();
231 }
232
233 try renderer.render();
234 return obj;
235}
236
237pub const Ref = enum(u32) { none = std.math.maxInt(u32), _ };
238
239pub const Inst = struct {
240 tag: Tag,
241 data: Data,
242 ty: Interner.Ref,
243
244 pub const Tag = enum {
245 // data.constant
246 // not included in blocks
247 constant,
248
249 // data.arg
250 // not included in blocks
251 arg,
252 symbol,
253
254 // data.label
255 label,
256
257 // data.block
258 label_addr,
259 jmp,
260
261 // data.switch
262 @"switch",
263
264 // data.branch
265 branch,
266 select,
267
268 // data.un
269 jmp_val,
270
271 // data.call
272 call,
273
274 // data.alloc
275 alloc,
276
277 // data.phi
278 phi,
279
280 // data.bin
281 store,
282 bit_or,
283 bit_xor,
284 bit_and,
285 bit_shl,
286 bit_shr,
287 cmp_eq,
288 cmp_ne,
289 cmp_lt,
290 cmp_lte,
291 cmp_gt,
292 cmp_gte,
293 add,
294 sub,
295 mul,
296 div,
297 mod,
298
299 // data.un
300 ret,
301 load,
302 bit_not,
303 negate,
304 trunc,
305 zext,
306 sext,
307 };
308
309 pub const Data = union {
310 constant: Interner.Ref,
311 none: void,
312 bin: struct {
313 lhs: Ref,
314 rhs: Ref,
315 },
316 un: Ref,
317 arg: u32,
318 alloc: struct {
319 size: u32,
320 @"align": u32,
321 },
322 @"switch": *Switch,
323 call: *Call,
324 label: [*:0]const u8,
325 branch: *Branch,
326 phi: Phi,
327 };
328
329 pub const Branch = struct {
330 cond: Ref,
331 then: Ref,
332 @"else": Ref,
333 };
334
335 pub const Switch = struct {
336 target: Ref,
337 cases_len: u32,
338 default: Ref,
339 case_vals: [*]Interner.Ref,
340 case_labels: [*]Ref,
341 };
342
343 pub const Call = struct {
344 func: Ref,
345 args_len: u32,
346 args_ptr: [*]Ref,
347
348 pub fn args(c: Call) []Ref {
349 return c.args_ptr[0..c.args_len];
350 }
351 };
352
353 pub const Phi = struct {
354 ptr: [*]Ir.Ref,
355
356 pub const Input = struct {
357 label: Ir.Ref,
358 value: Ir.Ref,
359 };
360
361 pub fn inputs(p: Phi) []Input {
362 const len = @intFromEnum(p.ptr[0]) * 2;
363 const slice = (p.ptr + 1)[0..len];
364 return std.mem.bytesAsSlice(Input, std.mem.sliceAsBytes(slice));
365 }
366 };
367};
368
369pub fn deinit(ir: *Ir, gpa: std.mem.Allocator) void {
370 for (ir.decls.values()) |*decl| {
371 decl.deinit(gpa);
372 }
373 ir.decls.deinit(gpa);
374 ir.* = undefined;
375}
376
377const TYPE = std.io.tty.Color.bright_magenta;
378const INST = std.io.tty.Color.bright_cyan;
379const REF = std.io.tty.Color.bright_blue;
380const LITERAL = std.io.tty.Color.bright_green;
381const ATTRIBUTE = std.io.tty.Color.bright_yellow;
382
383const RefMap = std.AutoArrayHashMap(Ref, void);
384
385pub fn dump(ir: *const Ir, gpa: Allocator, config: std.io.tty.Config, w: anytype) !void {
386 for (ir.decls.keys(), ir.decls.values()) |name, *decl| {
387 try ir.dumpDecl(decl, gpa, name, config, w);
388 }
389}
390
391fn dumpDecl(ir: *const Ir, decl: *const Decl, gpa: Allocator, name: []const u8, config: std.io.tty.Config, w: anytype) !void {
392 const tags = decl.instructions.items(.tag);
393 const data = decl.instructions.items(.data);
394
395 var ref_map = RefMap.init(gpa);
396 defer ref_map.deinit();
397
398 var label_map = RefMap.init(gpa);
399 defer label_map.deinit();
400
401 const ret_inst = decl.body.items[decl.body.items.len - 1];
402 const ret_operand = data[@intFromEnum(ret_inst)].un;
403 const ret_ty = decl.instructions.items(.ty)[@intFromEnum(ret_operand)];
404 try ir.writeType(ret_ty, config, w);
405 try config.setColor(w, REF);
406 try w.print(" @{s}", .{name});
407 try config.setColor(w, .reset);
408 try w.writeAll("(");
409
410 var arg_count: u32 = 0;
411 while (true) : (arg_count += 1) {
412 const ref = decl.body.items[arg_count];
413 if (tags[@intFromEnum(ref)] != .arg) break;
414 if (arg_count != 0) try w.writeAll(", ");
415 try ref_map.put(ref, {});
416 try ir.writeRef(decl, &ref_map, ref, config, w);
417 try config.setColor(w, .reset);
418 }
419 try w.writeAll(") {\n");
420 for (decl.body.items[arg_count..]) |ref| {
421 switch (tags[@intFromEnum(ref)]) {
422 .label => try label_map.put(ref, {}),
423 else => {},
424 }
425 }
426
427 for (decl.body.items[arg_count..]) |ref| {
428 const i = @intFromEnum(ref);
429 const tag = tags[i];
430 switch (tag) {
431 .arg, .constant, .symbol => unreachable,
432 .label => {
433 const label_index = label_map.getIndex(ref).?;
434 try config.setColor(w, REF);
435 try w.print("{s}.{d}:\n", .{ data[i].label, label_index });
436 },
437 // .label_val => {
438 // const un = data[i].un;
439 // try w.print(" %{d} = label.{d}\n", .{ i, @intFromEnum(un) });
440 // },
441 .jmp => {
442 const un = data[i].un;
443 try config.setColor(w, INST);
444 try w.writeAll(" jmp ");
445 try writeLabel(decl, &label_map, un, config, w);
446 try w.writeByte('\n');
447 },
448 .branch => {
449 const br = data[i].branch;
450 try config.setColor(w, INST);
451 try w.writeAll(" branch ");
452 try ir.writeRef(decl, &ref_map, br.cond, config, w);
453 try config.setColor(w, .reset);
454 try w.writeAll(", ");
455 try writeLabel(decl, &label_map, br.then, config, w);
456 try config.setColor(w, .reset);
457 try w.writeAll(", ");
458 try writeLabel(decl, &label_map, br.@"else", config, w);
459 try w.writeByte('\n');
460 },
461 .select => {
462 const br = data[i].branch;
463 try ir.writeNewRef(decl, &ref_map, ref, config, w);
464 try w.writeAll("select ");
465 try ir.writeRef(decl, &ref_map, br.cond, config, w);
466 try config.setColor(w, .reset);
467 try w.writeAll(", ");
468 try ir.writeRef(decl, &ref_map, br.then, config, w);
469 try config.setColor(w, .reset);
470 try w.writeAll(", ");
471 try ir.writeRef(decl, &ref_map, br.@"else", config, w);
472 try w.writeByte('\n');
473 },
474 // .jmp_val => {
475 // const bin = data[i].bin;
476 // try w.print(" %{s} %{d} label.{d}\n", .{ @tagName(tag), @intFromEnum(bin.lhs), @intFromEnum(bin.rhs) });
477 // },
478 .@"switch" => {
479 const @"switch" = data[i].@"switch";
480 try config.setColor(w, INST);
481 try w.writeAll(" switch ");
482 try ir.writeRef(decl, &ref_map, @"switch".target, config, w);
483 try config.setColor(w, .reset);
484 try w.writeAll(" {");
485 for (@"switch".case_vals[0..@"switch".cases_len], @"switch".case_labels) |val_ref, label_ref| {
486 try w.writeAll("\n ");
487 try ir.writeValue(val_ref, config, w);
488 try config.setColor(w, .reset);
489 try w.writeAll(" => ");
490 try writeLabel(decl, &label_map, label_ref, config, w);
491 try config.setColor(w, .reset);
492 }
493 try config.setColor(w, LITERAL);
494 try w.writeAll("\n default ");
495 try config.setColor(w, .reset);
496 try w.writeAll("=> ");
497 try writeLabel(decl, &label_map, @"switch".default, config, w);
498 try config.setColor(w, .reset);
499 try w.writeAll("\n }\n");
500 },
501 .call => {
502 const call = data[i].call;
503 try ir.writeNewRef(decl, &ref_map, ref, config, w);
504 try w.writeAll("call ");
505 try ir.writeRef(decl, &ref_map, call.func, config, w);
506 try config.setColor(w, .reset);
507 try w.writeAll("(");
508 for (call.args(), 0..) |arg, arg_i| {
509 if (arg_i != 0) try w.writeAll(", ");
510 try ir.writeRef(decl, &ref_map, arg, config, w);
511 try config.setColor(w, .reset);
512 }
513 try w.writeAll(")\n");
514 },
515 .alloc => {
516 const alloc = data[i].alloc;
517 try ir.writeNewRef(decl, &ref_map, ref, config, w);
518 try w.writeAll("alloc ");
519 try config.setColor(w, ATTRIBUTE);
520 try w.writeAll("size ");
521 try config.setColor(w, LITERAL);
522 try w.print("{d}", .{alloc.size});
523 try config.setColor(w, ATTRIBUTE);
524 try w.writeAll(" align ");
525 try config.setColor(w, LITERAL);
526 try w.print("{d}", .{alloc.@"align"});
527 try w.writeByte('\n');
528 },
529 .phi => {
530 try ir.writeNewRef(decl, &ref_map, ref, config, w);
531 try w.writeAll("phi");
532 try config.setColor(w, .reset);
533 try w.writeAll(" {");
534 for (data[i].phi.inputs()) |input| {
535 try w.writeAll("\n ");
536 try writeLabel(decl, &label_map, input.label, config, w);
537 try config.setColor(w, .reset);
538 try w.writeAll(" => ");
539 try ir.writeRef(decl, &ref_map, input.value, config, w);
540 try config.setColor(w, .reset);
541 }
542 try config.setColor(w, .reset);
543 try w.writeAll("\n }\n");
544 },
545 .store => {
546 const bin = data[i].bin;
547 try config.setColor(w, INST);
548 try w.writeAll(" store ");
549 try ir.writeRef(decl, &ref_map, bin.lhs, config, w);
550 try config.setColor(w, .reset);
551 try w.writeAll(", ");
552 try ir.writeRef(decl, &ref_map, bin.rhs, config, w);
553 try w.writeByte('\n');
554 },
555 .ret => {
556 try config.setColor(w, INST);
557 try w.writeAll(" ret ");
558 if (data[i].un != .none) try ir.writeRef(decl, &ref_map, data[i].un, config, w);
559 try w.writeByte('\n');
560 },
561 .load => {
562 try ir.writeNewRef(decl, &ref_map, ref, config, w);
563 try w.writeAll("load ");
564 try ir.writeRef(decl, &ref_map, data[i].un, config, w);
565 try w.writeByte('\n');
566 },
567 .bit_or,
568 .bit_xor,
569 .bit_and,
570 .bit_shl,
571 .bit_shr,
572 .cmp_eq,
573 .cmp_ne,
574 .cmp_lt,
575 .cmp_lte,
576 .cmp_gt,
577 .cmp_gte,
578 .add,
579 .sub,
580 .mul,
581 .div,
582 .mod,
583 => {
584 const bin = data[i].bin;
585 try ir.writeNewRef(decl, &ref_map, ref, config, w);
586 try w.print("{s} ", .{@tagName(tag)});
587 try ir.writeRef(decl, &ref_map, bin.lhs, config, w);
588 try config.setColor(w, .reset);
589 try w.writeAll(", ");
590 try ir.writeRef(decl, &ref_map, bin.rhs, config, w);
591 try w.writeByte('\n');
592 },
593 .bit_not,
594 .negate,
595 .trunc,
596 .zext,
597 .sext,
598 => {
599 const un = data[i].un;
600 try ir.writeNewRef(decl, &ref_map, ref, config, w);
601 try w.print("{s} ", .{@tagName(tag)});
602 try ir.writeRef(decl, &ref_map, un, config, w);
603 try w.writeByte('\n');
604 },
605 .label_addr, .jmp_val => {},
606 }
607 }
608 try config.setColor(w, .reset);
609 try w.writeAll("}\n\n");
610}
611
612fn writeType(ir: Ir, ty_ref: Interner.Ref, config: std.io.tty.Config, w: anytype) !void {
613 const ty = ir.interner.get(ty_ref);
614 try config.setColor(w, TYPE);
615 switch (ty) {
616 .ptr_ty, .noreturn_ty, .void_ty, .func_ty => try w.writeAll(@tagName(ty)),
617 .int_ty => |bits| try w.print("i{d}", .{bits}),
618 .float_ty => |bits| try w.print("f{d}", .{bits}),
619 .array_ty => |info| {
620 try w.print("[{d} * ", .{info.len});
621 try ir.writeType(info.child, .no_color, w);
622 try w.writeByte(']');
623 },
624 .vector_ty => |info| {
625 try w.print("<{d} * ", .{info.len});
626 try ir.writeType(info.child, .no_color, w);
627 try w.writeByte('>');
628 },
629 .record_ty => |elems| {
630 // TODO collect into buffer and only print once
631 try w.writeAll("{ ");
632 for (elems, 0..) |elem, i| {
633 if (i != 0) try w.writeAll(", ");
634 try ir.writeType(elem, config, w);
635 }
636 try w.writeAll(" }");
637 },
638 else => unreachable, // not a type
639 }
640}
641
642fn writeValue(ir: Ir, val: Interner.Ref, config: std.io.tty.Config, w: anytype) !void {
643 try config.setColor(w, LITERAL);
644 const key = ir.interner.get(val);
645 switch (key) {
646 .null => return w.writeAll("nullptr_t"),
647 .int => |repr| switch (repr) {
648 inline else => |x| return w.print("{d}", .{x}),
649 },
650 .float => |repr| switch (repr) {
651 inline else => |x| return w.print("{d}", .{@as(f64, @floatCast(x))}),
652 },
653 .bytes => |b| return std.zig.stringEscape(b, "", .{}, w),
654 else => unreachable, // not a value
655 }
656}
657
658fn writeRef(ir: Ir, decl: *const Decl, ref_map: *RefMap, ref: Ref, config: std.io.tty.Config, w: anytype) !void {
659 assert(ref != .none);
660 const index = @intFromEnum(ref);
661 const ty_ref = decl.instructions.items(.ty)[index];
662 if (decl.instructions.items(.tag)[index] == .constant) {
663 try ir.writeType(ty_ref, config, w);
664 const v_ref = decl.instructions.items(.data)[index].constant;
665 try w.writeByte(' ');
666 try ir.writeValue(v_ref, config, w);
667 return;
668 } else if (decl.instructions.items(.tag)[index] == .symbol) {
669 const name = decl.instructions.items(.data)[index].label;
670 try ir.writeType(ty_ref, config, w);
671 try config.setColor(w, REF);
672 try w.print(" @{s}", .{name});
673 return;
674 }
675 try ir.writeType(ty_ref, config, w);
676 try config.setColor(w, REF);
677 const ref_index = ref_map.getIndex(ref).?;
678 try w.print(" %{d}", .{ref_index});
679}
680
681fn writeNewRef(ir: Ir, decl: *const Decl, ref_map: *RefMap, ref: Ref, config: std.io.tty.Config, w: anytype) !void {
682 try ref_map.put(ref, {});
683 try w.writeAll(" ");
684 try ir.writeRef(decl, ref_map, ref, config, w);
685 try config.setColor(w, .reset);
686 try w.writeAll(" = ");
687 try config.setColor(w, INST);
688}
689
690fn writeLabel(decl: *const Decl, label_map: *RefMap, ref: Ref, config: std.io.tty.Config, w: anytype) !void {
691 assert(ref != .none);
692 const index = @intFromEnum(ref);
693 const label = decl.instructions.items(.data)[index].label;
694 try config.setColor(w, REF);
695 const label_index = label_map.getIndex(ref).?;
696 try w.print("{s}.{d}", .{ label, label_index });
697}
lib/compiler/aro/backend/Ir/x86/Renderer.zig deleted-65
...@@ -1,65 +0,0 @@
1const std = @import("std");
2const Allocator = std.mem.Allocator;
3const assert = std.debug.assert;
4const Interner = @import("../../Interner.zig");
5const Ir = @import("../../Ir.zig");
6const BaseRenderer = Ir.Renderer;
7const zig = @import("zig");
8const abi = zig.arch.x86_64.abi;
9const bits = zig.arch.x86_64.bits;
10
11const Condition = bits.Condition;
12const Immediate = bits.Immediate;
13const Memory = bits.Memory;
14const Register = bits.Register;
15const RegisterLock = RegisterManager.RegisterLock;
16const FrameIndex = bits.FrameIndex;
17
18const RegisterManager = zig.RegisterManager(Renderer, Register, Ir.Ref, abi.allocatable_regs);
19
20// Register classes
21const RegisterBitSet = RegisterManager.RegisterBitSet;
22const RegisterClass = struct {
23 const gp: RegisterBitSet = blk: {
24 var set = RegisterBitSet.initEmpty();
25 for (abi.allocatable_regs, 0..) |reg, index| if (reg.class() == .general_purpose) set.set(index);
26 break :blk set;
27 };
28 const x87: RegisterBitSet = blk: {
29 var set = RegisterBitSet.initEmpty();
30 for (abi.allocatable_regs, 0..) |reg, index| if (reg.class() == .x87) set.set(index);
31 break :blk set;
32 };
33 const sse: RegisterBitSet = blk: {
34 var set = RegisterBitSet.initEmpty();
35 for (abi.allocatable_regs, 0..) |reg, index| if (reg.class() == .sse) set.set(index);
36 break :blk set;
37 };
38};
39
40const Renderer = @This();
41
42base: *BaseRenderer,
43interner: *Interner,
44
45register_manager: RegisterManager = .{},
46
47pub fn render(base: *BaseRenderer) !void {
48 var renderer: Renderer = .{
49 .base = base,
50 .interner = base.ir.interner,
51 };
52
53 for (renderer.base.ir.decls.keys(), renderer.base.ir.decls.values()) |name, decl| {
54 renderer.renderFn(name, decl) catch |e| switch (e) {
55 error.OutOfMemory => return e,
56 error.LowerFail => continue,
57 };
58 }
59 if (renderer.base.errors.entries.len != 0) return error.LowerFail;
60}
61
62fn renderFn(r: *Renderer, name: []const u8, decl: Ir.Decl) !void {
63 _ = decl;
64 return r.base.fail(name, "TODO implement lowering functions", .{});
65}
lib/compiler/aro/backend/Object.zig deleted-73
...@@ -1,73 +0,0 @@
1const std = @import("std");
2const Allocator = std.mem.Allocator;
3const Elf = @import("Object/Elf.zig");
4
5const Object = @This();
6
7format: std.Target.ObjectFormat,
8target: std.Target,
9
10pub fn create(gpa: Allocator, target: std.Target) !*Object {
11 switch (target.ofmt) {
12 .elf => return Elf.create(gpa, target),
13 else => unreachable,
14 }
15}
16
17pub fn deinit(obj: *Object) void {
18 switch (obj.format) {
19 .elf => @as(*Elf, @alignCast(@fieldParentPtr("obj", obj))).deinit(),
20 else => unreachable,
21 }
22}
23
24pub const Section = union(enum) {
25 undefined,
26 data,
27 read_only_data,
28 func,
29 strings,
30 custom: []const u8,
31};
32
33pub fn getSection(obj: *Object, section: Section) !*std.ArrayList(u8) {
34 switch (obj.format) {
35 .elf => return @as(*Elf, @alignCast(@fieldParentPtr("obj", obj))).getSection(section),
36 else => unreachable,
37 }
38}
39
40pub const SymbolType = enum {
41 func,
42 variable,
43 external,
44};
45
46pub fn declareSymbol(
47 obj: *Object,
48 section: Section,
49 name: ?[]const u8,
50 linkage: std.builtin.GlobalLinkage,
51 @"type": SymbolType,
52 offset: u64,
53 size: u64,
54) ![]const u8 {
55 switch (obj.format) {
56 .elf => return @as(*Elf, @alignCast(@fieldParentPtr("obj", obj))).declareSymbol(section, name, linkage, @"type", offset, size),
57 else => unreachable,
58 }
59}
60
61pub fn addRelocation(obj: *Object, name: []const u8, section: Section, address: u64, addend: i64) !void {
62 switch (obj.format) {
63 .elf => return @as(*Elf, @alignCast(@fieldParentPtr("obj", obj))).addRelocation(name, section, address, addend),
64 else => unreachable,
65 }
66}
67
68pub fn finish(obj: *Object, file: std.fs.File) !void {
69 switch (obj.format) {
70 .elf => return @as(*Elf, @alignCast(@fieldParentPtr("obj", obj))).finish(file),
71 else => unreachable,
72 }
73}
lib/compiler/aro/backend/Object/Elf.zig deleted-378
...@@ -1,378 +0,0 @@
1const std = @import("std");
2const Allocator = std.mem.Allocator;
3const Target = std.Target;
4const Object = @import("../Object.zig");
5
6const Section = struct {
7 data: std.ArrayList(u8),
8 relocations: std.ArrayListUnmanaged(Relocation) = .empty,
9 flags: u64,
10 type: u32,
11 index: u16 = undefined,
12};
13
14const Symbol = struct {
15 section: ?*Section,
16 size: u64,
17 offset: u64,
18 index: u16 = undefined,
19 info: u8,
20};
21
22const Relocation = struct {
23 symbol: *Symbol,
24 addend: i64,
25 offset: u48,
26 type: u8,
27};
28
29const additional_sections = 3; // null section, strtab, symtab
30const strtab_index = 1;
31const symtab_index = 2;
32const strtab_default = "\x00.strtab\x00.symtab\x00";
33const strtab_name = 1;
34const symtab_name = "\x00.strtab\x00".len;
35
36const Elf = @This();
37
38obj: Object,
39/// The keys are owned by the Codegen.tree
40sections: std.StringHashMapUnmanaged(*Section) = .empty,
41local_symbols: std.StringHashMapUnmanaged(*Symbol) = .empty,
42global_symbols: std.StringHashMapUnmanaged(*Symbol) = .empty,
43unnamed_symbol_mangle: u32 = 0,
44strtab_len: u64 = strtab_default.len,
45arena: std.heap.ArenaAllocator,
46
47pub fn create(gpa: Allocator, target: Target) !*Object {
48 const elf = try gpa.create(Elf);
49 elf.* = .{
50 .obj = .{ .format = .elf, .target = target },
51 .arena = std.heap.ArenaAllocator.init(gpa),
52 };
53 return &elf.obj;
54}
55
56pub fn deinit(elf: *Elf) void {
57 const gpa = elf.arena.child_allocator;
58 {
59 var it = elf.sections.valueIterator();
60 while (it.next()) |sect| {
61 sect.*.data.deinit();
62 sect.*.relocations.deinit(gpa);
63 }
64 }
65 elf.sections.deinit(gpa);
66 elf.local_symbols.deinit(gpa);
67 elf.global_symbols.deinit(gpa);
68 elf.arena.deinit();
69 gpa.destroy(elf);
70}
71
72fn sectionString(sec: Object.Section) []const u8 {
73 return switch (sec) {
74 .undefined => unreachable,
75 .data => "data",
76 .read_only_data => "rodata",
77 .func => "text",
78 .strings => "rodata.str",
79 .custom => |name| name,
80 };
81}
82
83pub fn getSection(elf: *Elf, section_kind: Object.Section) !*std.ArrayList(u8) {
84 const section_name = sectionString(section_kind);
85 const section = elf.sections.get(section_name) orelse blk: {
86 const section = try elf.arena.allocator().create(Section);
87 section.* = .{
88 .data = std.ArrayList(u8).init(elf.arena.child_allocator),
89 .type = std.elf.SHT_PROGBITS,
90 .flags = switch (section_kind) {
91 .func, .custom => std.elf.SHF_ALLOC + std.elf.SHF_EXECINSTR,
92 .strings => std.elf.SHF_ALLOC + std.elf.SHF_MERGE + std.elf.SHF_STRINGS,
93 .read_only_data => std.elf.SHF_ALLOC,
94 .data => std.elf.SHF_ALLOC + std.elf.SHF_WRITE,
95 .undefined => unreachable,
96 },
97 };
98 try elf.sections.putNoClobber(elf.arena.child_allocator, section_name, section);
99 elf.strtab_len += section_name.len + ".\x00".len;
100 break :blk section;
101 };
102 return &section.data;
103}
104
105pub fn declareSymbol(
106 elf: *Elf,
107 section_kind: Object.Section,
108 maybe_name: ?[]const u8,
109 linkage: std.builtin.GlobalLinkage,
110 @"type": Object.SymbolType,
111 offset: u64,
112 size: u64,
113) ![]const u8 {
114 const section = blk: {
115 if (section_kind == .undefined) break :blk null;
116 const section_name = sectionString(section_kind);
117 break :blk elf.sections.get(section_name);
118 };
119 const binding: u8 = switch (linkage) {
120 .Internal => std.elf.STB_LOCAL,
121 .Strong => std.elf.STB_GLOBAL,
122 .Weak => std.elf.STB_WEAK,
123 .LinkOnce => unreachable,
124 };
125 const sym_type: u8 = switch (@"type") {
126 .func => std.elf.STT_FUNC,
127 .variable => std.elf.STT_OBJECT,
128 .external => std.elf.STT_NOTYPE,
129 };
130 const name = if (maybe_name) |some| some else blk: {
131 defer elf.unnamed_symbol_mangle += 1;
132 break :blk try std.fmt.allocPrint(elf.arena.allocator(), ".L.{d}", .{elf.unnamed_symbol_mangle});
133 };
134
135 const gop = if (linkage == .Internal)
136 try elf.local_symbols.getOrPut(elf.arena.child_allocator, name)
137 else
138 try elf.global_symbols.getOrPut(elf.arena.child_allocator, name);
139
140 if (!gop.found_existing) {
141 gop.value_ptr.* = try elf.arena.allocator().create(Symbol);
142 elf.strtab_len += name.len + 1; // +1 for null byte
143 }
144 gop.value_ptr.*.* = .{
145 .section = section,
146 .size = size,
147 .offset = offset,
148 .info = (binding << 4) + sym_type,
149 };
150 return name;
151}
152
153pub fn addRelocation(elf: *Elf, name: []const u8, section_kind: Object.Section, address: u64, addend: i64) !void {
154 const section_name = sectionString(section_kind);
155 const symbol = elf.local_symbols.get(name) orelse elf.global_symbols.get(name).?; // reference to undeclared symbol
156 const section = elf.sections.get(section_name).?;
157 if (section.relocations.items.len == 0) elf.strtab_len += ".rela".len;
158
159 try section.relocations.append(elf.arena.child_allocator, .{
160 .symbol = symbol,
161 .offset = @intCast(address),
162 .addend = addend,
163 .type = if (symbol.section == null) 4 else 2, // TODO
164 });
165}
166
167/// elf header
168/// sections contents
169/// symbols
170/// relocations
171/// strtab
172/// section headers
173pub fn finish(elf: *Elf, file: std.fs.File) !void {
174 var buf_writer = std.io.bufferedWriter(file.writer());
175 const w = buf_writer.writer();
176
177 var num_sections: std.elf.Elf64_Half = additional_sections;
178 var relocations_len: std.elf.Elf64_Off = 0;
179 var sections_len: std.elf.Elf64_Off = 0;
180 {
181 var it = elf.sections.valueIterator();
182 while (it.next()) |sect| {
183 sections_len += sect.*.data.items.len;
184 relocations_len += sect.*.relocations.items.len * @sizeOf(std.elf.Elf64_Rela);
185 sect.*.index = num_sections;
186 num_sections += 1;
187 num_sections += @intFromBool(sect.*.relocations.items.len != 0);
188 }
189 }
190 const symtab_len = (elf.local_symbols.count() + elf.global_symbols.count() + 1) * @sizeOf(std.elf.Elf64_Sym);
191
192 const symtab_offset = @sizeOf(std.elf.Elf64_Ehdr) + sections_len;
193 const symtab_offset_aligned = std.mem.alignForward(u64, symtab_offset, 8);
194 const rela_offset = symtab_offset_aligned + symtab_len;
195 const strtab_offset = rela_offset + relocations_len;
196 const sh_offset = strtab_offset + elf.strtab_len;
197 const sh_offset_aligned = std.mem.alignForward(u64, sh_offset, 16);
198
199 const elf_header = std.elf.Elf64_Ehdr{
200 .e_ident = .{ 0x7F, 'E', 'L', 'F', 2, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
201 .e_type = std.elf.ET.REL, // we only produce relocatables
202 .e_machine = elf.obj.target.toElfMachine(),
203 .e_version = 1,
204 .e_entry = 0, // linker will handle this
205 .e_phoff = 0, // no program header
206 .e_shoff = sh_offset_aligned, // section headers offset
207 .e_flags = 0, // no flags
208 .e_ehsize = @sizeOf(std.elf.Elf64_Ehdr),
209 .e_phentsize = 0, // no program header
210 .e_phnum = 0, // no program header
211 .e_shentsize = @sizeOf(std.elf.Elf64_Shdr),
212 .e_shnum = num_sections,
213 .e_shstrndx = strtab_index,
214 };
215 try w.writeStruct(elf_header);
216
217 // write contents of sections
218 {
219 var it = elf.sections.valueIterator();
220 while (it.next()) |sect| try w.writeAll(sect.*.data.items);
221 }
222
223 // pad to 8 bytes
224 try w.writeByteNTimes(0, @intCast(symtab_offset_aligned - symtab_offset));
225
226 var name_offset: u32 = strtab_default.len;
227 // write symbols
228 {
229 // first symbol must be null
230 try w.writeStruct(std.mem.zeroes(std.elf.Elf64_Sym));
231
232 var sym_index: u16 = 1;
233 var it = elf.local_symbols.iterator();
234 while (it.next()) |entry| {
235 const sym = entry.value_ptr.*;
236 try w.writeStruct(std.elf.Elf64_Sym{
237 .st_name = name_offset,
238 .st_info = sym.info,
239 .st_other = 0,
240 .st_shndx = if (sym.section) |some| some.index else 0,
241 .st_value = sym.offset,
242 .st_size = sym.size,
243 });
244 sym.index = sym_index;
245 sym_index += 1;
246 name_offset += @intCast(entry.key_ptr.len + 1); // +1 for null byte
247 }
248 it = elf.global_symbols.iterator();
249 while (it.next()) |entry| {
250 const sym = entry.value_ptr.*;
251 try w.writeStruct(std.elf.Elf64_Sym{
252 .st_name = name_offset,
253 .st_info = sym.info,
254 .st_other = 0,
255 .st_shndx = if (sym.section) |some| some.index else 0,
256 .st_value = sym.offset,
257 .st_size = sym.size,
258 });
259 sym.index = sym_index;
260 sym_index += 1;
261 name_offset += @intCast(entry.key_ptr.len + 1); // +1 for null byte
262 }
263 }
264
265 // write relocations
266 {
267 var it = elf.sections.valueIterator();
268 while (it.next()) |sect| {
269 for (sect.*.relocations.items) |rela| {
270 try w.writeStruct(std.elf.Elf64_Rela{
271 .r_offset = rela.offset,
272 .r_addend = rela.addend,
273 .r_info = (@as(u64, rela.symbol.index) << 32) | rela.type,
274 });
275 }
276 }
277 }
278
279 // write strtab
280 try w.writeAll(strtab_default);
281 {
282 var it = elf.local_symbols.keyIterator();
283 while (it.next()) |key| try w.print("{s}\x00", .{key.*});
284 it = elf.global_symbols.keyIterator();
285 while (it.next()) |key| try w.print("{s}\x00", .{key.*});
286 }
287 {
288 var it = elf.sections.iterator();
289 while (it.next()) |entry| {
290 if (entry.value_ptr.*.relocations.items.len != 0) try w.writeAll(".rela");
291 try w.print(".{s}\x00", .{entry.key_ptr.*});
292 }
293 }
294
295 // pad to 16 bytes
296 try w.writeByteNTimes(0, @intCast(sh_offset_aligned - sh_offset));
297 // mandatory null header
298 try w.writeStruct(std.mem.zeroes(std.elf.Elf64_Shdr));
299
300 // write strtab section header
301 {
302 const sect_header = std.elf.Elf64_Shdr{
303 .sh_name = strtab_name,
304 .sh_type = std.elf.SHT_STRTAB,
305 .sh_flags = 0,
306 .sh_addr = 0,
307 .sh_offset = strtab_offset,
308 .sh_size = elf.strtab_len,
309 .sh_link = 0,
310 .sh_info = 0,
311 .sh_addralign = 1,
312 .sh_entsize = 0,
313 };
314 try w.writeStruct(sect_header);
315 }
316
317 // write symtab section header
318 {
319 const sect_header = std.elf.Elf64_Shdr{
320 .sh_name = symtab_name,
321 .sh_type = std.elf.SHT_SYMTAB,
322 .sh_flags = 0,
323 .sh_addr = 0,
324 .sh_offset = symtab_offset_aligned,
325 .sh_size = symtab_len,
326 .sh_link = strtab_index,
327 .sh_info = elf.local_symbols.size + 1,
328 .sh_addralign = 8,
329 .sh_entsize = @sizeOf(std.elf.Elf64_Sym),
330 };
331 try w.writeStruct(sect_header);
332 }
333
334 // remaining section headers
335 {
336 var sect_offset: u64 = @sizeOf(std.elf.Elf64_Ehdr);
337 var rela_sect_offset: u64 = rela_offset;
338 var it = elf.sections.iterator();
339 while (it.next()) |entry| {
340 const sect = entry.value_ptr.*;
341 const rela_count = sect.relocations.items.len;
342 const rela_name_offset: u32 = if (rela_count != 0) @truncate(".rela".len) else 0;
343 try w.writeStruct(std.elf.Elf64_Shdr{
344 .sh_name = rela_name_offset + name_offset,
345 .sh_type = sect.type,
346 .sh_flags = sect.flags,
347 .sh_addr = 0,
348 .sh_offset = sect_offset,
349 .sh_size = sect.data.items.len,
350 .sh_link = 0,
351 .sh_info = 0,
352 .sh_addralign = if (sect.flags & std.elf.SHF_EXECINSTR != 0) 16 else 1,
353 .sh_entsize = 0,
354 });
355
356 if (rela_count != 0) {
357 const size = rela_count * @sizeOf(std.elf.Elf64_Rela);
358 try w.writeStruct(std.elf.Elf64_Shdr{
359 .sh_name = name_offset,
360 .sh_type = std.elf.SHT_RELA,
361 .sh_flags = 0,
362 .sh_addr = 0,
363 .sh_offset = rela_sect_offset,
364 .sh_size = rela_count * @sizeOf(std.elf.Elf64_Rela),
365 .sh_link = symtab_index,
366 .sh_info = sect.index,
367 .sh_addralign = 8,
368 .sh_entsize = @sizeOf(std.elf.Elf64_Rela),
369 });
370 rela_sect_offset += size;
371 }
372
373 sect_offset += sect.data.items.len;
374 name_offset += @as(u32, @intCast(entry.key_ptr.len + ".\x00".len)) + rela_name_offset;
375 }
376 }
377 try buf_writer.flush();
378}
lib/compiler/aro_translate_c.zig deleted-1814
...@@ -1,1814 +0,0 @@
1const std = @import("std");
2const mem = std.mem;
3const assert = std.debug.assert;
4const CallingConvention = std.builtin.CallingConvention;
5const aro = @import("aro");
6const CToken = aro.Tokenizer.Token;
7const Tree = aro.Tree;
8const NodeIndex = Tree.NodeIndex;
9const TokenIndex = Tree.TokenIndex;
10const Type = aro.Type;
11pub const ast = @import("aro_translate_c/ast.zig");
12const ZigNode = ast.Node;
13const ZigTag = ZigNode.Tag;
14const Scope = ScopeExtra(Context, Type);
15const Context = @This();
16
17gpa: mem.Allocator,
18arena: mem.Allocator,
19decl_table: std.AutoArrayHashMapUnmanaged(usize, []const u8) = .empty,
20alias_list: AliasList,
21global_scope: *Scope.Root,
22mangle_count: u32 = 0,
23/// Table of record decls that have been demoted to opaques.
24opaque_demotes: std.AutoHashMapUnmanaged(usize, void) = .empty,
25/// Table of unnamed enums and records that are child types of typedefs.
26unnamed_typedefs: std.AutoHashMapUnmanaged(usize, []const u8) = .empty,
27/// Needed to decide if we are parsing a typename
28typedefs: std.StringArrayHashMapUnmanaged(void) = .empty,
29
30/// This one is different than the root scope's name table. This contains
31/// a list of names that we found by visiting all the top level decls without
32/// translating them. The other maps are updated as we translate; this one is updated
33/// up front in a pre-processing step.
34global_names: std.StringArrayHashMapUnmanaged(void) = .empty,
35
36/// This is similar to `global_names`, but contains names which we would
37/// *like* to use, but do not strictly *have* to if they are unavailable.
38/// These are relevant to types, which ideally we would name like
39/// 'struct_foo' with an alias 'foo', but if either of those names is taken,
40/// may be mangled.
41/// This is distinct from `global_names` so we can detect at a type
42/// declaration whether or not the name is available.
43weak_global_names: std.StringArrayHashMapUnmanaged(void) = .empty,
44
45pattern_list: PatternList,
46tree: Tree,
47comp: *aro.Compilation,
48mapper: aro.TypeMapper,
49
50fn getMangle(c: *Context) u32 {
51 c.mangle_count += 1;
52 return c.mangle_count;
53}
54
55/// Convert an aro TokenIndex to a 'file:line:column' string
56fn locStr(c: *Context, tok_idx: TokenIndex) ![]const u8 {
57 const token_loc = c.tree.tokens.items(.loc)[tok_idx];
58 const source = c.comp.getSource(token_loc.id);
59 const line_col = source.lineCol(token_loc);
60 const filename = source.path;
61
62 const line = source.physicalLine(token_loc);
63 const col = line_col.col;
64
65 return std.fmt.allocPrint(c.arena, "{s}:{d}:{d}", .{ filename, line, col });
66}
67
68fn maybeSuppressResult(c: *Context, used: ResultUsed, result: ZigNode) TransError!ZigNode {
69 if (used == .used) return result;
70 return ZigTag.discard.create(c.arena, .{ .should_skip = false, .value = result });
71}
72
73fn addTopLevelDecl(c: *Context, name: []const u8, decl_node: ZigNode) !void {
74 const gop = try c.global_scope.sym_table.getOrPut(name);
75 if (!gop.found_existing) {
76 gop.value_ptr.* = decl_node;
77 try c.global_scope.nodes.append(decl_node);
78 }
79}
80
81fn fail(
82 c: *Context,
83 err: anytype,
84 source_loc: TokenIndex,
85 comptime format: []const u8,
86 args: anytype,
87) (@TypeOf(err) || error{OutOfMemory}) {
88 try warn(c, &c.global_scope.base, source_loc, format, args);
89 return err;
90}
91
92fn failDecl(c: *Context, loc: TokenIndex, name: []const u8, comptime format: []const u8, args: anytype) Error!void {
93 // location
94 // pub const name = @compileError(msg);
95 const fail_msg = try std.fmt.allocPrint(c.arena, format, args);
96 try addTopLevelDecl(c, name, try ZigTag.fail_decl.create(c.arena, .{ .actual = name, .mangled = fail_msg }));
97 const str = try c.locStr(loc);
98 const location_comment = try std.fmt.allocPrint(c.arena, "// {s}", .{str});
99 try c.global_scope.nodes.append(try ZigTag.warning.create(c.arena, location_comment));
100}
101
102fn warn(c: *Context, scope: *Scope, loc: TokenIndex, comptime format: []const u8, args: anytype) !void {
103 const str = try c.locStr(loc);
104 const value = try std.fmt.allocPrint(c.arena, "// {s}: warning: " ++ format, .{str} ++ args);
105 try scope.appendNode(try ZigTag.warning.create(c.arena, value));
106}
107
108pub fn translate(
109 gpa: mem.Allocator,
110 comp: *aro.Compilation,
111 args: []const []const u8,
112) !std.zig.Ast {
113 try comp.addDefaultPragmaHandlers();
114 comp.langopts.setEmulatedCompiler(aro.target_util.systemCompiler(comp.target));
115
116 var driver: aro.Driver = .{ .comp = comp };
117 defer driver.deinit();
118
119 var macro_buf = std.ArrayList(u8).init(gpa);
120 defer macro_buf.deinit();
121
122 assert(!try driver.parseArgs(std.io.null_writer, macro_buf.writer(), args));
123 assert(driver.inputs.items.len == 1);
124 const source = driver.inputs.items[0];
125
126 const builtin_macros = try comp.generateBuiltinMacros(.include_system_defines);
127 const user_macros = try comp.addSourceFromBuffer("<command line>", macro_buf.items);
128
129 var pp = try aro.Preprocessor.initDefault(comp);
130 defer pp.deinit();
131
132 try pp.preprocessSources(&.{ source, builtin_macros, user_macros });
133
134 var tree = try pp.parse();
135 defer tree.deinit();
136
137 // Workaround for https://github.com/Vexu/arocc/issues/603
138 for (comp.diagnostics.list.items) |msg| {
139 if (msg.kind == .@"error" or msg.kind == .@"fatal error") return error.ParsingFailed;
140 }
141
142 const mapper = tree.comp.string_interner.getFastTypeMapper(tree.comp.gpa) catch tree.comp.string_interner.getSlowTypeMapper();
143 defer mapper.deinit(tree.comp.gpa);
144
145 var arena_allocator = std.heap.ArenaAllocator.init(gpa);
146 defer arena_allocator.deinit();
147 const arena = arena_allocator.allocator();
148
149 var context = Context{
150 .gpa = gpa,
151 .arena = arena,
152 .alias_list = AliasList.init(gpa),
153 .global_scope = try arena.create(Scope.Root),
154 .pattern_list = try PatternList.init(gpa),
155 .comp = comp,
156 .mapper = mapper,
157 .tree = tree,
158 };
159 context.global_scope.* = Scope.Root.init(&context);
160 defer {
161 context.decl_table.deinit(gpa);
162 context.alias_list.deinit();
163 context.global_names.deinit(gpa);
164 context.opaque_demotes.deinit(gpa);
165 context.unnamed_typedefs.deinit(gpa);
166 context.typedefs.deinit(gpa);
167 context.global_scope.deinit();
168 context.pattern_list.deinit(gpa);
169 }
170
171 inline for (@typeInfo(std.zig.c_builtins).@"struct".decls) |decl| {
172 const builtin_fn = try ZigTag.pub_var_simple.create(arena, .{
173 .name = decl.name,
174 .init = try ZigTag.import_c_builtin.create(arena, decl.name),
175 });
176 try addTopLevelDecl(&context, decl.name, builtin_fn);
177 }
178
179 try prepopulateGlobalNameTable(&context);
180 try transTopLevelDecls(&context);
181
182 for (context.alias_list.items) |alias| {
183 if (!context.global_scope.sym_table.contains(alias.alias)) {
184 const node = try ZigTag.alias.create(arena, .{ .actual = alias.alias, .mangled = alias.name });
185 try addTopLevelDecl(&context, alias.alias, node);
186 }
187 }
188
189 return ast.render(gpa, context.global_scope.nodes.items);
190}
191
192fn prepopulateGlobalNameTable(c: *Context) !void {
193 const node_tags = c.tree.nodes.items(.tag);
194 const node_types = c.tree.nodes.items(.ty);
195 const node_data = c.tree.nodes.items(.data);
196 for (c.tree.root_decls) |node| {
197 const data = node_data[@intFromEnum(node)];
198 switch (node_tags[@intFromEnum(node)]) {
199 .typedef => {},
200
201 .struct_decl_two,
202 .union_decl_two,
203 .struct_decl,
204 .union_decl,
205 .struct_forward_decl,
206 .union_forward_decl,
207 .enum_decl_two,
208 .enum_decl,
209 .enum_forward_decl,
210 => {
211 const raw_ty = node_types[@intFromEnum(node)];
212 const ty = raw_ty.canonicalize(.standard);
213 const name_id = if (ty.isRecord()) ty.data.record.name else ty.data.@"enum".name;
214 const decl_name = c.mapper.lookup(name_id);
215 const container_prefix = if (ty.is(.@"struct")) "struct" else if (ty.is(.@"union")) "union" else "enum";
216 const prefixed_name = try std.fmt.allocPrint(c.arena, "{s}_{s}", .{ container_prefix, decl_name });
217 // `decl_name` and `prefixed_name` are the preferred names for this type.
218 // However, we can name it anything else if necessary, so these are "weak names".
219 try c.weak_global_names.ensureUnusedCapacity(c.gpa, 2);
220 c.weak_global_names.putAssumeCapacity(decl_name, {});
221 c.weak_global_names.putAssumeCapacity(prefixed_name, {});
222 },
223
224 .fn_proto,
225 .static_fn_proto,
226 .inline_fn_proto,
227 .inline_static_fn_proto,
228 .fn_def,
229 .static_fn_def,
230 .inline_fn_def,
231 .inline_static_fn_def,
232 .@"var",
233 .extern_var,
234 .static_var,
235 .threadlocal_var,
236 .threadlocal_extern_var,
237 .threadlocal_static_var,
238 => {
239 const decl_name = c.tree.tokSlice(data.decl.name);
240 try c.global_names.put(c.gpa, decl_name, {});
241 },
242 .static_assert => {},
243 else => unreachable,
244 }
245 }
246}
247
248fn transTopLevelDecls(c: *Context) !void {
249 for (c.tree.root_decls) |node| {
250 try transDecl(c, &c.global_scope.base, node);
251 }
252}
253
254fn transDecl(c: *Context, scope: *Scope, decl: NodeIndex) !void {
255 const node_tags = c.tree.nodes.items(.tag);
256 const node_data = c.tree.nodes.items(.data);
257 const node_ty = c.tree.nodes.items(.ty);
258 const data = node_data[@intFromEnum(decl)];
259 switch (node_tags[@intFromEnum(decl)]) {
260 .typedef => {
261 try transTypeDef(c, scope, decl);
262 },
263
264 .struct_decl_two,
265 .union_decl_two,
266 => {
267 try transRecordDecl(c, scope, node_ty[@intFromEnum(decl)]);
268 },
269 .struct_decl,
270 .union_decl,
271 => {
272 try transRecordDecl(c, scope, node_ty[@intFromEnum(decl)]);
273 },
274
275 .enum_decl_two => {
276 var fields = [2]NodeIndex{ data.bin.lhs, data.bin.rhs };
277 var field_count: u8 = 0;
278 if (fields[0] != .none) field_count += 1;
279 if (fields[1] != .none) field_count += 1;
280 const enum_decl = node_ty[@intFromEnum(decl)].canonicalize(.standard).data.@"enum";
281 try transEnumDecl(c, scope, enum_decl, fields[0..field_count]);
282 },
283 .enum_decl => {
284 const fields = c.tree.data[data.range.start..data.range.end];
285 const enum_decl = node_ty[@intFromEnum(decl)].canonicalize(.standard).data.@"enum";
286 try transEnumDecl(c, scope, enum_decl, fields);
287 },
288
289 .enum_field_decl,
290 .record_field_decl,
291 .indirect_record_field_decl,
292 .struct_forward_decl,
293 .union_forward_decl,
294 .enum_forward_decl,
295 => return,
296
297 .fn_proto,
298 .static_fn_proto,
299 .inline_fn_proto,
300 .inline_static_fn_proto,
301 .fn_def,
302 .static_fn_def,
303 .inline_fn_def,
304 .inline_static_fn_def,
305 => {
306 try transFnDecl(c, decl, true);
307 },
308
309 .@"var",
310 .extern_var,
311 .static_var,
312 .threadlocal_var,
313 .threadlocal_extern_var,
314 .threadlocal_static_var,
315 => {
316 try transVarDecl(c, decl);
317 },
318 .static_assert => try warn(c, &c.global_scope.base, 0, "ignoring _Static_assert declaration", .{}),
319 else => unreachable,
320 }
321}
322
323fn transTypeDef(c: *Context, scope: *Scope, typedef_decl: NodeIndex) Error!void {
324 const ty = c.tree.nodes.items(.ty)[@intFromEnum(typedef_decl)];
325 const data = c.tree.nodes.items(.data)[@intFromEnum(typedef_decl)];
326
327 const toplevel = scope.id == .root;
328 const bs: *Scope.Block = if (!toplevel) try scope.findBlockScope(c) else undefined;
329
330 var name: []const u8 = c.tree.tokSlice(data.decl.name);
331 try c.typedefs.put(c.gpa, name, {});
332
333 if (!toplevel) name = try bs.makeMangledName(c, name);
334
335 const typedef_loc = data.decl.name;
336 const init_node = transType(c, scope, ty, .standard, typedef_loc) catch |err| switch (err) {
337 error.UnsupportedType => {
338 return failDecl(c, typedef_loc, name, "unable to resolve typedef child type", .{});
339 },
340 error.OutOfMemory => |e| return e,
341 };
342
343 const payload = try c.arena.create(ast.Payload.SimpleVarDecl);
344 payload.* = .{
345 .base = .{ .tag = ([2]ZigTag{ .var_simple, .pub_var_simple })[@intFromBool(toplevel)] },
346 .data = .{
347 .name = name,
348 .init = init_node,
349 },
350 };
351 const node = ZigNode.initPayload(&payload.base);
352
353 if (toplevel) {
354 try addTopLevelDecl(c, name, node);
355 } else {
356 try scope.appendNode(node);
357 if (node.tag() != .pub_var_simple) {
358 try bs.discardVariable(c, name);
359 }
360 }
361}
362
363fn mangleWeakGlobalName(c: *Context, want_name: []const u8) ![]const u8 {
364 var cur_name = want_name;
365
366 if (!c.weak_global_names.contains(want_name)) {
367 // This type wasn't noticed by the name detection pass, so nothing has been treating this as
368 // a weak global name. We must mangle it to avoid conflicts with locals.
369 cur_name = try std.fmt.allocPrint(c.arena, "{s}_{d}", .{ want_name, c.getMangle() });
370 }
371
372 while (c.global_names.contains(cur_name)) {
373 cur_name = try std.fmt.allocPrint(c.arena, "{s}_{d}", .{ want_name, c.getMangle() });
374 }
375 return cur_name;
376}
377
378fn transRecordDecl(c: *Context, scope: *Scope, record_ty: Type) Error!void {
379 const record_decl = record_ty.getRecord().?;
380 if (c.decl_table.get(@intFromPtr(record_decl))) |_|
381 return; // Avoid processing this decl twice
382 const toplevel = scope.id == .root;
383 const bs: *Scope.Block = if (!toplevel) try scope.findBlockScope(c) else undefined;
384
385 const container_kind: ZigTag = if (record_ty.is(.@"union")) .@"union" else .@"struct";
386 const container_kind_name: []const u8 = @tagName(container_kind);
387
388 var is_unnamed = false;
389 var bare_name: []const u8 = c.mapper.lookup(record_decl.name);
390 var name = bare_name;
391
392 if (c.unnamed_typedefs.get(@intFromPtr(record_decl))) |typedef_name| {
393 bare_name = typedef_name;
394 name = typedef_name;
395 } else {
396 if (record_ty.isAnonymousRecord(c.comp)) {
397 bare_name = try std.fmt.allocPrint(c.arena, "unnamed_{d}", .{c.getMangle()});
398 is_unnamed = true;
399 }
400 name = try std.fmt.allocPrint(c.arena, "{s}_{s}", .{ container_kind_name, bare_name });
401 if (toplevel and !is_unnamed) {
402 name = try mangleWeakGlobalName(c, name);
403 }
404 }
405 if (!toplevel) name = try bs.makeMangledName(c, name);
406 try c.decl_table.putNoClobber(c.gpa, @intFromPtr(record_decl), name);
407
408 const is_pub = toplevel and !is_unnamed;
409 const init_node = blk: {
410 if (record_decl.isIncomplete()) {
411 try c.opaque_demotes.put(c.gpa, @intFromPtr(record_decl), {});
412 break :blk ZigTag.opaque_literal.init();
413 }
414
415 var fields = try std.ArrayList(ast.Payload.Record.Field).initCapacity(c.gpa, record_decl.fields.len);
416 defer fields.deinit();
417
418 // TODO: Add support for flexible array field functions
419 var functions = std.ArrayList(ZigNode).init(c.gpa);
420 defer functions.deinit();
421
422 var unnamed_field_count: u32 = 0;
423
424 // If a record doesn't have any attributes that would affect the alignment and
425 // layout, then we can just use a simple `extern` type. If it does have attributes,
426 // then we need to inspect the layout and assign an `align` value for each field.
427 const has_alignment_attributes = record_decl.field_attributes != null or
428 record_ty.hasAttribute(.@"packed") or
429 record_ty.hasAttribute(.aligned);
430 const head_field_alignment: ?c_uint = if (has_alignment_attributes) headFieldAlignment(record_decl) else null;
431
432 for (record_decl.fields, 0..) |field, field_index| {
433 const field_loc = field.name_tok;
434
435 // Demote record to opaque if it contains a bitfield
436 if (!field.isRegularField()) {
437 try c.opaque_demotes.put(c.gpa, @intFromPtr(record_decl), {});
438 try warn(c, scope, field_loc, "{s} demoted to opaque type - has bitfield", .{container_kind_name});
439 break :blk ZigTag.opaque_literal.init();
440 }
441
442 var field_name = c.mapper.lookup(field.name);
443 if (!field.isNamed()) {
444 field_name = try std.fmt.allocPrint(c.arena, "unnamed_{d}", .{unnamed_field_count});
445 unnamed_field_count += 1;
446 }
447 const field_type = transType(c, scope, field.ty, .preserve_quals, field_loc) catch |err| switch (err) {
448 error.UnsupportedType => {
449 try c.opaque_demotes.put(c.gpa, @intFromPtr(record_decl), {});
450 try warn(c, scope, 0, "{s} demoted to opaque type - unable to translate type of field {s}", .{
451 container_kind_name,
452 field_name,
453 });
454 break :blk ZigTag.opaque_literal.init();
455 },
456 else => |e| return e,
457 };
458
459 const field_alignment = if (has_alignment_attributes)
460 alignmentForField(record_decl, head_field_alignment, field_index)
461 else
462 null;
463
464 // C99 introduced designated initializers for structs. Omitted fields are implicitly
465 // initialized to zero. Some C APIs are designed with this in mind. Defaulting to zero
466 // values for translated struct fields permits Zig code to comfortably use such an API.
467 const default_value = if (container_kind == .@"struct")
468 try ZigTag.std_mem_zeroes.create(c.arena, field_type)
469 else
470 null;
471
472 fields.appendAssumeCapacity(.{
473 .name = field_name,
474 .type = field_type,
475 .alignment = field_alignment,
476 .default_value = default_value,
477 });
478 }
479
480 const record_payload = try c.arena.create(ast.Payload.Record);
481 record_payload.* = .{
482 .base = .{ .tag = container_kind },
483 .data = .{
484 .layout = .@"extern",
485 .fields = try c.arena.dupe(ast.Payload.Record.Field, fields.items),
486 .functions = try c.arena.dupe(ZigNode, functions.items),
487 .variables = &.{},
488 },
489 };
490 break :blk ZigNode.initPayload(&record_payload.base);
491 };
492
493 const payload = try c.arena.create(ast.Payload.SimpleVarDecl);
494 payload.* = .{
495 .base = .{ .tag = ([2]ZigTag{ .var_simple, .pub_var_simple })[@intFromBool(is_pub)] },
496 .data = .{
497 .name = name,
498 .init = init_node,
499 },
500 };
501 const node = ZigNode.initPayload(&payload.base);
502 if (toplevel) {
503 try addTopLevelDecl(c, name, node);
504 // Only add the alias if the name is available *and* it was caught by
505 // name detection. Don't bother performing a weak mangle, since a
506 // mangled name is of no real use here.
507 if (!is_unnamed and !c.global_names.contains(bare_name) and c.weak_global_names.contains(bare_name))
508 try c.alias_list.append(.{ .alias = bare_name, .name = name });
509 } else {
510 try scope.appendNode(node);
511 if (node.tag() != .pub_var_simple) {
512 try bs.discardVariable(c, name);
513 }
514 }
515}
516
517fn transFnDecl(c: *Context, fn_decl: NodeIndex, is_pub: bool) Error!void {
518 const raw_ty = c.tree.nodes.items(.ty)[@intFromEnum(fn_decl)];
519 const fn_ty = raw_ty.canonicalize(.standard);
520 const node_data = c.tree.nodes.items(.data)[@intFromEnum(fn_decl)];
521 if (c.decl_table.get(@intFromPtr(fn_ty.data.func))) |_|
522 return; // Avoid processing this decl twice
523
524 const fn_name = c.tree.tokSlice(node_data.decl.name);
525 if (c.global_scope.sym_table.contains(fn_name))
526 return; // Avoid processing this decl twice
527
528 const fn_decl_loc = 0; // TODO
529 const has_body = node_data.decl.node != .none;
530 const is_always_inline = has_body and raw_ty.getAttribute(.always_inline) != null;
531 const proto_ctx = FnProtoContext{
532 .fn_name = fn_name,
533 .is_inline = is_always_inline,
534 .is_extern = !has_body,
535 .is_export = switch (c.tree.nodes.items(.tag)[@intFromEnum(fn_decl)]) {
536 .fn_proto, .fn_def => has_body and !is_always_inline,
537
538 .inline_fn_proto, .inline_fn_def, .inline_static_fn_proto, .inline_static_fn_def, .static_fn_proto, .static_fn_def => false,
539
540 else => unreachable,
541 },
542 .is_pub = is_pub,
543 };
544
545 const proto_node = transFnType(c, &c.global_scope.base, raw_ty, fn_ty, fn_decl_loc, proto_ctx) catch |err| switch (err) {
546 error.UnsupportedType => {
547 return failDecl(c, fn_decl_loc, fn_name, "unable to resolve prototype of function", .{});
548 },
549 error.OutOfMemory => |e| return e,
550 };
551
552 if (!has_body) {
553 return addTopLevelDecl(c, fn_name, proto_node);
554 }
555 const proto_payload = proto_node.castTag(.func).?;
556
557 // actual function definition with body
558 const body_stmt = node_data.decl.node;
559 var block_scope = try Scope.Block.init(c, &c.global_scope.base, false);
560 block_scope.return_type = fn_ty.data.func.return_type;
561 defer block_scope.deinit();
562
563 var scope = &block_scope.base;
564 _ = &scope;
565
566 var param_id: c_uint = 0;
567 for (proto_payload.data.params, fn_ty.data.func.params) |*param, param_info| {
568 const param_name = param.name orelse {
569 proto_payload.data.is_extern = true;
570 proto_payload.data.is_export = false;
571 proto_payload.data.is_inline = false;
572 try warn(c, &c.global_scope.base, fn_decl_loc, "function {s} parameter has no name, demoted to extern", .{fn_name});
573 return addTopLevelDecl(c, fn_name, proto_node);
574 };
575
576 const is_const = param_info.ty.qual.@"const";
577
578 const mangled_param_name = try block_scope.makeMangledName(c, param_name);
579 param.name = mangled_param_name;
580
581 if (!is_const) {
582 const bare_arg_name = try std.fmt.allocPrint(c.arena, "arg_{s}", .{mangled_param_name});
583 const arg_name = try block_scope.makeMangledName(c, bare_arg_name);
584 param.name = arg_name;
585
586 const redecl_node = try ZigTag.arg_redecl.create(c.arena, .{ .actual = mangled_param_name, .mangled = arg_name });
587 try block_scope.statements.append(redecl_node);
588 }
589 try block_scope.discardVariable(c, mangled_param_name);
590
591 param_id += 1;
592 }
593
594 transCompoundStmtInline(c, body_stmt, &block_scope) catch |err| switch (err) {
595 error.OutOfMemory => |e| return e,
596 error.UnsupportedTranslation,
597 error.UnsupportedType,
598 => {
599 proto_payload.data.is_extern = true;
600 proto_payload.data.is_export = false;
601 proto_payload.data.is_inline = false;
602 try warn(c, &c.global_scope.base, fn_decl_loc, "unable to translate function, demoted to extern", .{});
603 return addTopLevelDecl(c, fn_name, proto_node);
604 },
605 };
606
607 proto_payload.data.body = try block_scope.complete(c);
608 return addTopLevelDecl(c, fn_name, proto_node);
609}
610
611fn transVarDecl(c: *Context, node: NodeIndex) Error!void {
612 const data = c.tree.nodes.items(.data)[@intFromEnum(node)];
613 const name = c.tree.tokSlice(data.decl.name);
614 return failDecl(c, data.decl.name, name, "unable to translate variable declaration", .{});
615}
616
617fn transEnumDecl(c: *Context, scope: *Scope, enum_decl: *const Type.Enum, field_nodes: []const NodeIndex) Error!void {
618 if (c.decl_table.get(@intFromPtr(enum_decl))) |_|
619 return; // Avoid processing this decl twice
620 const toplevel = scope.id == .root;
621 const bs: *Scope.Block = if (!toplevel) try scope.findBlockScope(c) else undefined;
622
623 var is_unnamed = false;
624 var bare_name: []const u8 = c.mapper.lookup(enum_decl.name);
625 var name = bare_name;
626 if (c.unnamed_typedefs.get(@intFromPtr(enum_decl))) |typedef_name| {
627 bare_name = typedef_name;
628 name = typedef_name;
629 } else {
630 if (bare_name.len == 0) {
631 bare_name = try std.fmt.allocPrint(c.arena, "unnamed_{d}", .{c.getMangle()});
632 is_unnamed = true;
633 }
634 name = try std.fmt.allocPrint(c.arena, "enum_{s}", .{bare_name});
635 }
636 if (!toplevel) name = try bs.makeMangledName(c, name);
637 try c.decl_table.putNoClobber(c.gpa, @intFromPtr(enum_decl), name);
638
639 const enum_type_node = if (!enum_decl.isIncomplete()) blk: {
640 for (enum_decl.fields, field_nodes) |field, field_node| {
641 var enum_val_name: []const u8 = c.mapper.lookup(field.name);
642 if (!toplevel) {
643 enum_val_name = try bs.makeMangledName(c, enum_val_name);
644 }
645
646 const enum_const_type_node: ?ZigNode = transType(c, scope, field.ty, .standard, field.name_tok) catch |err| switch (err) {
647 error.UnsupportedType => null,
648 else => |e| return e,
649 };
650
651 const val = c.tree.value_map.get(field_node).?;
652 const enum_const_def = try ZigTag.enum_constant.create(c.arena, .{
653 .name = enum_val_name,
654 .is_public = toplevel,
655 .type = enum_const_type_node,
656 .value = try transCreateNodeAPInt(c, val),
657 });
658 if (toplevel)
659 try addTopLevelDecl(c, enum_val_name, enum_const_def)
660 else {
661 try scope.appendNode(enum_const_def);
662 try bs.discardVariable(c, enum_val_name);
663 }
664 }
665
666 break :blk transType(c, scope, enum_decl.tag_ty, .standard, 0) catch |err| switch (err) {
667 error.UnsupportedType => {
668 return failDecl(c, 0, name, "unable to translate enum integer type", .{});
669 },
670 else => |e| return e,
671 };
672 } else blk: {
673 try c.opaque_demotes.put(c.gpa, @intFromPtr(enum_decl), {});
674 break :blk ZigTag.opaque_literal.init();
675 };
676
677 const is_pub = toplevel and !is_unnamed;
678 const payload = try c.arena.create(ast.Payload.SimpleVarDecl);
679 payload.* = .{
680 .base = .{ .tag = ([2]ZigTag{ .var_simple, .pub_var_simple })[@intFromBool(is_pub)] },
681 .data = .{
682 .init = enum_type_node,
683 .name = name,
684 },
685 };
686 const node = ZigNode.initPayload(&payload.base);
687 if (toplevel) {
688 try addTopLevelDecl(c, name, node);
689 if (!is_unnamed)
690 try c.alias_list.append(.{ .alias = bare_name, .name = name });
691 } else {
692 try scope.appendNode(node);
693 if (node.tag() != .pub_var_simple) {
694 try bs.discardVariable(c, name);
695 }
696 }
697}
698
699fn getTypeStr(c: *Context, ty: Type) ![]const u8 {
700 var buf: std.ArrayListUnmanaged(u8) = .empty;
701 defer buf.deinit(c.gpa);
702 const w = buf.writer(c.gpa);
703 try ty.print(c.mapper, c.comp.langopts, w);
704 return c.arena.dupe(u8, buf.items);
705}
706
707fn transType(c: *Context, scope: *Scope, raw_ty: Type, qual_handling: Type.QualHandling, source_loc: TokenIndex) TypeError!ZigNode {
708 const ty = raw_ty.canonicalize(qual_handling);
709 if (ty.qual.atomic) {
710 const type_name = try getTypeStr(c, ty);
711 return fail(c, error.UnsupportedType, source_loc, "unsupported type: '{s}'", .{type_name});
712 }
713
714 switch (ty.specifier) {
715 .void => return ZigTag.type.create(c.arena, "anyopaque"),
716 .bool => return ZigTag.type.create(c.arena, "bool"),
717 .char => return ZigTag.type.create(c.arena, "c_char"),
718 .schar => return ZigTag.type.create(c.arena, "i8"),
719 .uchar => return ZigTag.type.create(c.arena, "u8"),
720 .short => return ZigTag.type.create(c.arena, "c_short"),
721 .ushort => return ZigTag.type.create(c.arena, "c_ushort"),
722 .int => return ZigTag.type.create(c.arena, "c_int"),
723 .uint => return ZigTag.type.create(c.arena, "c_uint"),
724 .long => return ZigTag.type.create(c.arena, "c_long"),
725 .ulong => return ZigTag.type.create(c.arena, "c_ulong"),
726 .long_long => return ZigTag.type.create(c.arena, "c_longlong"),
727 .ulong_long => return ZigTag.type.create(c.arena, "c_ulonglong"),
728 .int128 => return ZigTag.type.create(c.arena, "i128"),
729 .uint128 => return ZigTag.type.create(c.arena, "u128"),
730 .fp16, .float16 => return ZigTag.type.create(c.arena, "f16"),
731 .float => return ZigTag.type.create(c.arena, "f32"),
732 .double => return ZigTag.type.create(c.arena, "f64"),
733 .long_double => return ZigTag.type.create(c.arena, "c_longdouble"),
734 .float128 => return ZigTag.type.create(c.arena, "f128"),
735 .@"enum" => {
736 const enum_decl = ty.data.@"enum";
737 var trans_scope = scope;
738 if (enum_decl.name != .empty) {
739 const decl_name = c.mapper.lookup(enum_decl.name);
740 if (c.weak_global_names.contains(decl_name)) trans_scope = &c.global_scope.base;
741 }
742 try transEnumDecl(c, trans_scope, enum_decl, &.{});
743 return ZigTag.identifier.create(c.arena, c.decl_table.get(@intFromPtr(enum_decl)).?);
744 },
745 .pointer => {
746 const child_type = ty.elemType();
747
748 const is_fn_proto = child_type.isFunc();
749 const is_const = is_fn_proto or child_type.isConst();
750 const is_volatile = child_type.qual.@"volatile";
751 const elem_type = try transType(c, scope, child_type, qual_handling, source_loc);
752 const ptr_info: @FieldType(ast.Payload.Pointer, "data") = .{
753 .is_const = is_const,
754 .is_volatile = is_volatile,
755 .elem_type = elem_type,
756 };
757 if (is_fn_proto or
758 typeIsOpaque(c, child_type) or
759 typeWasDemotedToOpaque(c, child_type))
760 {
761 const ptr = try ZigTag.single_pointer.create(c.arena, ptr_info);
762 return ZigTag.optional_type.create(c.arena, ptr);
763 }
764
765 return ZigTag.c_pointer.create(c.arena, ptr_info);
766 },
767 .unspecified_variable_len_array, .incomplete_array => {
768 const child_type = ty.elemType();
769 const is_const = child_type.qual.@"const";
770 const is_volatile = child_type.qual.@"volatile";
771 const elem_type = try transType(c, scope, child_type, qual_handling, source_loc);
772
773 return ZigTag.c_pointer.create(c.arena, .{ .is_const = is_const, .is_volatile = is_volatile, .elem_type = elem_type });
774 },
775 .array,
776 .static_array,
777 => {
778 const size = ty.arrayLen().?;
779 const elem_type = try transType(c, scope, ty.elemType(), qual_handling, source_loc);
780 return ZigTag.array_type.create(c.arena, .{ .len = size, .elem_type = elem_type });
781 },
782 .func,
783 .var_args_func,
784 .old_style_func,
785 => return transFnType(c, scope, ty, ty, source_loc, .{}),
786 .@"struct",
787 .@"union",
788 => {
789 var trans_scope = scope;
790 if (ty.isAnonymousRecord(c.comp)) {
791 const record_decl = ty.data.record;
792 const name_id = c.mapper.lookup(record_decl.name);
793 if (c.weak_global_names.contains(name_id)) trans_scope = &c.global_scope.base;
794 }
795 try transRecordDecl(c, trans_scope, ty);
796 const name = c.decl_table.get(@intFromPtr(ty.data.record)).?;
797 return ZigTag.identifier.create(c.arena, name);
798 },
799 .attributed,
800 .typeof_type,
801 .typeof_expr,
802 => unreachable,
803 else => return error.UnsupportedType,
804 }
805}
806
807/// Look ahead through the fields of the record to determine what the alignment of the record
808/// would be without any align/packed/etc. attributes. This helps us determine whether or not
809/// the fields with 0 offset need an `align` qualifier. Strictly speaking, we could just
810/// pedantically assign those fields the same alignment as the parent's pointer alignment,
811/// but this helps the generated code to be a little less verbose.
812fn headFieldAlignment(record_decl: *const Type.Record) ?c_uint {
813 const bits_per_byte = 8;
814 const parent_ptr_alignment_bits = record_decl.type_layout.pointer_alignment_bits;
815 const parent_ptr_alignment = parent_ptr_alignment_bits / bits_per_byte;
816 var max_field_alignment_bits: u64 = 0;
817 for (record_decl.fields) |field| {
818 if (field.ty.getRecord()) |field_record_decl| {
819 const child_record_alignment = field_record_decl.type_layout.field_alignment_bits;
820 if (child_record_alignment > max_field_alignment_bits)
821 max_field_alignment_bits = child_record_alignment;
822 } else {
823 const field_size = field.layout.size_bits;
824 if (field_size > max_field_alignment_bits)
825 max_field_alignment_bits = field_size;
826 }
827 }
828 if (max_field_alignment_bits != parent_ptr_alignment_bits) {
829 return parent_ptr_alignment;
830 } else {
831 return null;
832 }
833}
834
835/// This function inspects the generated layout of a record to determine the alignment for a
836/// particular field. This approach is necessary because unlike Zig, a C compiler is not
837/// required to fulfill the requested alignment, which means we'd risk generating different code
838/// if we only look at the user-requested alignment.
839///
840/// Returns a ?c_uint to match Clang's behaviour of using c_uint. The return type can be changed
841/// after the Clang frontend for translate-c is removed. A null value indicates that a field is
842/// 'naturally aligned'.
843fn alignmentForField(
844 record_decl: *const Type.Record,
845 head_field_alignment: ?c_uint,
846 field_index: usize,
847) ?c_uint {
848 const fields = record_decl.fields;
849 assert(fields.len != 0);
850 const field = fields[field_index];
851
852 const bits_per_byte = 8;
853 const parent_ptr_alignment_bits = record_decl.type_layout.pointer_alignment_bits;
854 const parent_ptr_alignment = parent_ptr_alignment_bits / bits_per_byte;
855
856 // bitfields aren't supported yet. Until support is added, records with bitfields
857 // should be demoted to opaque, and this function shouldn't be called for them.
858 if (!field.isRegularField()) {
859 @panic("TODO: add bitfield support for records");
860 }
861
862 const field_offset_bits: u64 = field.layout.offset_bits;
863 const field_size_bits: u64 = field.layout.size_bits;
864
865 // Fields with zero width always have an alignment of 1
866 if (field_size_bits == 0) {
867 return 1;
868 }
869
870 // Fields with 0 offset inherit the parent's pointer alignment.
871 if (field_offset_bits == 0) {
872 return head_field_alignment;
873 }
874
875 // Records have a natural alignment when used as a field, and their size is
876 // a multiple of this alignment value. For all other types, the natural alignment
877 // is their size.
878 const field_natural_alignment_bits: u64 = if (field.ty.getRecord()) |record| record.type_layout.field_alignment_bits else field_size_bits;
879 const rem_bits = field_offset_bits % field_natural_alignment_bits;
880
881 // If there's a remainder, then the alignment is smaller than the field's
882 // natural alignment
883 if (rem_bits > 0) {
884 const rem_alignment = rem_bits / bits_per_byte;
885 if (rem_alignment > 0 and std.math.isPowerOfTwo(rem_alignment)) {
886 const actual_alignment = @min(rem_alignment, parent_ptr_alignment);
887 return @as(c_uint, @truncate(actual_alignment));
888 } else {
889 return 1;
890 }
891 }
892
893 // A field may have an offset which positions it to be naturally aligned, but the
894 // parent's pointer alignment determines if this is actually true, so we take the minimum
895 // value.
896 // For example, a float field (4 bytes wide) with a 4 byte offset is positioned to have natural
897 // alignment, but if the parent pointer alignment is 2, then the actual alignment of the
898 // float is 2.
899 const field_natural_alignment: u64 = field_natural_alignment_bits / bits_per_byte;
900 const offset_alignment = field_offset_bits / bits_per_byte;
901 const possible_alignment = @min(parent_ptr_alignment, offset_alignment);
902 if (possible_alignment == field_natural_alignment) {
903 return null;
904 } else if (possible_alignment < field_natural_alignment) {
905 if (std.math.isPowerOfTwo(possible_alignment)) {
906 return possible_alignment;
907 } else {
908 return 1;
909 }
910 } else { // possible_alignment > field_natural_alignment
911 // Here, the field is positioned be at a higher alignment than it's natural alignment. This means we
912 // need to determine whether it's a specified alignment. We can determine that from the padding preceding
913 // the field.
914 const padding_from_prev_field: u64 = blk: {
915 if (field_offset_bits != 0) {
916 const previous_field = fields[field_index - 1];
917 break :blk (field_offset_bits - previous_field.layout.offset_bits) - previous_field.layout.size_bits;
918 } else {
919 break :blk 0;
920 }
921 };
922 if (padding_from_prev_field < field_natural_alignment_bits) {
923 return null;
924 } else {
925 return possible_alignment;
926 }
927 }
928}
929
930const FnProtoContext = struct {
931 is_pub: bool = false,
932 is_export: bool = false,
933 is_extern: bool = false,
934 is_inline: bool = false,
935 fn_name: ?[]const u8 = null,
936};
937
938fn transFnType(
939 c: *Context,
940 scope: *Scope,
941 raw_ty: Type,
942 fn_ty: Type,
943 source_loc: TokenIndex,
944 ctx: FnProtoContext,
945) !ZigNode {
946 const param_count: usize = fn_ty.data.func.params.len;
947 const fn_params = try c.arena.alloc(ast.Payload.Param, param_count);
948
949 for (fn_ty.data.func.params, fn_params) |param_info, *param_node| {
950 const param_ty = param_info.ty;
951 const is_noalias = param_ty.qual.restrict;
952
953 const param_name: ?[]const u8 = if (param_info.name == .empty)
954 null
955 else
956 c.mapper.lookup(param_info.name);
957
958 const type_node = try transType(c, scope, param_ty, .standard, param_info.name_tok);
959 param_node.* = .{
960 .is_noalias = is_noalias,
961 .name = param_name,
962 .type = type_node,
963 };
964 }
965
966 const linksection_string = blk: {
967 if (raw_ty.getAttribute(.section)) |section| {
968 break :blk c.comp.interner.get(section.name.ref()).bytes;
969 }
970 break :blk null;
971 };
972
973 const alignment: ?c_uint = raw_ty.requestedAlignment(c.comp) orelse null;
974
975 const explicit_callconv = null;
976 // const explicit_callconv = if ((ctx.is_inline or ctx.is_export or ctx.is_extern) and ctx.cc == .C) null else ctx.cc;
977
978 const return_type_node = blk: {
979 if (raw_ty.getAttribute(.noreturn) != null) {
980 break :blk ZigTag.noreturn_type.init();
981 } else {
982 const return_ty = fn_ty.data.func.return_type;
983 if (return_ty.is(.void)) {
984 // convert primitive anyopaque to actual void (only for return type)
985 break :blk ZigTag.void_type.init();
986 } else {
987 break :blk transType(c, scope, return_ty, .standard, source_loc) catch |err| switch (err) {
988 error.UnsupportedType => {
989 try warn(c, scope, source_loc, "unsupported function proto return type", .{});
990 return err;
991 },
992 error.OutOfMemory => |e| return e,
993 };
994 }
995 }
996 };
997
998 const payload = try c.arena.create(ast.Payload.Func);
999 payload.* = .{
1000 .base = .{ .tag = .func },
1001 .data = .{
1002 .is_pub = ctx.is_pub,
1003 .is_extern = ctx.is_extern,
1004 .is_export = ctx.is_export,
1005 .is_inline = ctx.is_inline,
1006 .is_var_args = switch (fn_ty.specifier) {
1007 .func => false,
1008 .var_args_func => true,
1009 .old_style_func => !ctx.is_export and !ctx.is_inline,
1010 else => unreachable,
1011 },
1012 .name = ctx.fn_name,
1013 .linksection_string = linksection_string,
1014 .explicit_callconv = explicit_callconv,
1015 .params = fn_params,
1016 .return_type = return_type_node,
1017 .body = null,
1018 .alignment = alignment,
1019 },
1020 };
1021 return ZigNode.initPayload(&payload.base);
1022}
1023
1024fn transStmt(c: *Context, node: NodeIndex) TransError!ZigNode {
1025 _ = c;
1026 _ = node;
1027 return error.UnsupportedTranslation;
1028}
1029
1030fn transCompoundStmtInline(c: *Context, compound: NodeIndex, block: *Scope.Block) TransError!void {
1031 const data = c.tree.nodes.items(.data)[@intFromEnum(compound)];
1032 var buf: [2]NodeIndex = undefined;
1033 // TODO move these helpers to Aro
1034 const stmts = switch (c.tree.nodes.items(.tag)[@intFromEnum(compound)]) {
1035 .compound_stmt_two => blk: {
1036 if (data.bin.lhs != .none) buf[0] = data.bin.lhs;
1037 if (data.bin.rhs != .none) buf[1] = data.bin.rhs;
1038 break :blk buf[0 .. @as(u32, @intFromBool(data.bin.lhs != .none)) + @intFromBool(data.bin.rhs != .none)];
1039 },
1040 .compound_stmt => c.tree.data[data.range.start..data.range.end],
1041 else => unreachable,
1042 };
1043 for (stmts) |stmt| {
1044 const result = try transStmt(c, stmt);
1045 switch (result.tag()) {
1046 .declaration, .empty_block => {},
1047 else => try block.statements.append(result),
1048 }
1049 }
1050}
1051
1052fn recordHasBitfield(record: *const Type.Record) bool {
1053 if (record.isIncomplete()) return false;
1054 for (record.fields) |field| {
1055 if (!field.isRegularField()) return true;
1056 }
1057 return false;
1058}
1059
1060fn typeIsOpaque(c: *Context, ty: Type) bool {
1061 return switch (ty.specifier) {
1062 .void => true,
1063 .@"struct", .@"union" => recordHasBitfield(ty.getRecord().?),
1064 .typeof_type => typeIsOpaque(c, ty.data.sub_type.*),
1065 .typeof_expr => typeIsOpaque(c, ty.data.expr.ty),
1066 .attributed => typeIsOpaque(c, ty.data.attributed.base),
1067 else => false,
1068 };
1069}
1070
1071fn typeWasDemotedToOpaque(c: *Context, ty: Type) bool {
1072 switch (ty.specifier) {
1073 .@"struct", .@"union" => {
1074 const record = ty.getRecord().?;
1075 if (c.opaque_demotes.contains(@intFromPtr(record))) return true;
1076 for (record.fields) |field| {
1077 if (typeWasDemotedToOpaque(c, field.ty)) return true;
1078 }
1079 return false;
1080 },
1081
1082 .@"enum" => return c.opaque_demotes.contains(@intFromPtr(ty.data.@"enum")),
1083
1084 .typeof_type => return typeWasDemotedToOpaque(c, ty.data.sub_type.*),
1085 .typeof_expr => return typeWasDemotedToOpaque(c, ty.data.expr.ty),
1086 .attributed => return typeWasDemotedToOpaque(c, ty.data.attributed.base),
1087 else => return false,
1088 }
1089}
1090
1091fn transCompoundStmt(c: *Context, scope: *Scope, compound: NodeIndex) TransError!ZigNode {
1092 var block_scope = try Scope.Block.init(c, scope, false);
1093 defer block_scope.deinit();
1094 try transCompoundStmtInline(c, compound, &block_scope);
1095 return try block_scope.complete(c);
1096}
1097
1098fn transExpr(c: *Context, node: NodeIndex, result_used: ResultUsed) TransError!ZigNode {
1099 std.debug.assert(node != .none);
1100 const ty = c.tree.nodes.items(.ty)[@intFromEnum(node)];
1101 if (c.tree.value_map.get(node)) |val| {
1102 // TODO handle other values
1103 const int = try transCreateNodeAPInt(c, val);
1104 const as_node = try ZigTag.as.create(c.arena, .{
1105 .lhs = try transType(c, undefined, ty, .standard, undefined),
1106 .rhs = int,
1107 });
1108 return maybeSuppressResult(c, result_used, as_node);
1109 }
1110 const node_tags = c.tree.nodes.items(.tag);
1111 switch (node_tags[@intFromEnum(node)]) {
1112 else => unreachable, // Not an expression.
1113 }
1114 return .none;
1115}
1116
1117fn transCreateNodeAPInt(c: *Context, int: aro.Value) !ZigNode {
1118 var space: aro.Interner.Tag.Int.BigIntSpace = undefined;
1119 var big = int.toBigInt(&space, c.comp);
1120 const is_negative = !big.positive;
1121 big.positive = true;
1122
1123 const str = big.toStringAlloc(c.arena, 10, .lower) catch |err| switch (err) {
1124 error.OutOfMemory => return error.OutOfMemory,
1125 };
1126 const res = try ZigTag.integer_literal.create(c.arena, str);
1127 if (is_negative) return ZigTag.negate.create(c.arena, res);
1128 return res;
1129}
1130
1131pub const PatternList = struct {
1132 patterns: []Pattern,
1133
1134 /// Templates must be function-like macros
1135 /// first element is macro source, second element is the name of the function
1136 /// in std.lib.zig.c_translation.Macros which implements it
1137 const templates = [_][2][]const u8{
1138 [2][]const u8{ "f_SUFFIX(X) (X ## f)", "F_SUFFIX" },
1139 [2][]const u8{ "F_SUFFIX(X) (X ## F)", "F_SUFFIX" },
1140
1141 [2][]const u8{ "u_SUFFIX(X) (X ## u)", "U_SUFFIX" },
1142 [2][]const u8{ "U_SUFFIX(X) (X ## U)", "U_SUFFIX" },
1143
1144 [2][]const u8{ "l_SUFFIX(X) (X ## l)", "L_SUFFIX" },
1145 [2][]const u8{ "L_SUFFIX(X) (X ## L)", "L_SUFFIX" },
1146
1147 [2][]const u8{ "ul_SUFFIX(X) (X ## ul)", "UL_SUFFIX" },
1148 [2][]const u8{ "uL_SUFFIX(X) (X ## uL)", "UL_SUFFIX" },
1149 [2][]const u8{ "Ul_SUFFIX(X) (X ## Ul)", "UL_SUFFIX" },
1150 [2][]const u8{ "UL_SUFFIX(X) (X ## UL)", "UL_SUFFIX" },
1151
1152 [2][]const u8{ "ll_SUFFIX(X) (X ## ll)", "LL_SUFFIX" },
1153 [2][]const u8{ "LL_SUFFIX(X) (X ## LL)", "LL_SUFFIX" },
1154
1155 [2][]const u8{ "ull_SUFFIX(X) (X ## ull)", "ULL_SUFFIX" },
1156 [2][]const u8{ "uLL_SUFFIX(X) (X ## uLL)", "ULL_SUFFIX" },
1157 [2][]const u8{ "Ull_SUFFIX(X) (X ## Ull)", "ULL_SUFFIX" },
1158 [2][]const u8{ "ULL_SUFFIX(X) (X ## ULL)", "ULL_SUFFIX" },
1159
1160 [2][]const u8{ "f_SUFFIX(X) X ## f", "F_SUFFIX" },
1161 [2][]const u8{ "F_SUFFIX(X) X ## F", "F_SUFFIX" },
1162
1163 [2][]const u8{ "u_SUFFIX(X) X ## u", "U_SUFFIX" },
1164 [2][]const u8{ "U_SUFFIX(X) X ## U", "U_SUFFIX" },
1165
1166 [2][]const u8{ "l_SUFFIX(X) X ## l", "L_SUFFIX" },
1167 [2][]const u8{ "L_SUFFIX(X) X ## L", "L_SUFFIX" },
1168
1169 [2][]const u8{ "ul_SUFFIX(X) X ## ul", "UL_SUFFIX" },
1170 [2][]const u8{ "uL_SUFFIX(X) X ## uL", "UL_SUFFIX" },
1171 [2][]const u8{ "Ul_SUFFIX(X) X ## Ul", "UL_SUFFIX" },
1172 [2][]const u8{ "UL_SUFFIX(X) X ## UL", "UL_SUFFIX" },
1173
1174 [2][]const u8{ "ll_SUFFIX(X) X ## ll", "LL_SUFFIX" },
1175 [2][]const u8{ "LL_SUFFIX(X) X ## LL", "LL_SUFFIX" },
1176
1177 [2][]const u8{ "ull_SUFFIX(X) X ## ull", "ULL_SUFFIX" },
1178 [2][]const u8{ "uLL_SUFFIX(X) X ## uLL", "ULL_SUFFIX" },
1179 [2][]const u8{ "Ull_SUFFIX(X) X ## Ull", "ULL_SUFFIX" },
1180 [2][]const u8{ "ULL_SUFFIX(X) X ## ULL", "ULL_SUFFIX" },
1181
1182 [2][]const u8{ "CAST_OR_CALL(X, Y) (X)(Y)", "CAST_OR_CALL" },
1183 [2][]const u8{ "CAST_OR_CALL(X, Y) ((X)(Y))", "CAST_OR_CALL" },
1184
1185 [2][]const u8{
1186 \\wl_container_of(ptr, sample, member) \
1187 \\(__typeof__(sample))((char *)(ptr) - \
1188 \\ offsetof(__typeof__(*sample), member))
1189 ,
1190 "WL_CONTAINER_OF",
1191 },
1192
1193 [2][]const u8{ "IGNORE_ME(X) ((void)(X))", "DISCARD" },
1194 [2][]const u8{ "IGNORE_ME(X) (void)(X)", "DISCARD" },
1195 [2][]const u8{ "IGNORE_ME(X) ((const void)(X))", "DISCARD" },
1196 [2][]const u8{ "IGNORE_ME(X) (const void)(X)", "DISCARD" },
1197 [2][]const u8{ "IGNORE_ME(X) ((volatile void)(X))", "DISCARD" },
1198 [2][]const u8{ "IGNORE_ME(X) (volatile void)(X)", "DISCARD" },
1199 [2][]const u8{ "IGNORE_ME(X) ((const volatile void)(X))", "DISCARD" },
1200 [2][]const u8{ "IGNORE_ME(X) (const volatile void)(X)", "DISCARD" },
1201 [2][]const u8{ "IGNORE_ME(X) ((volatile const void)(X))", "DISCARD" },
1202 [2][]const u8{ "IGNORE_ME(X) (volatile const void)(X)", "DISCARD" },
1203 };
1204
1205 /// Assumes that `ms` represents a tokenized function-like macro.
1206 fn buildArgsHash(allocator: mem.Allocator, ms: MacroSlicer, hash: *ArgsPositionMap) MacroProcessingError!void {
1207 assert(ms.tokens.len > 2);
1208 assert(ms.tokens[0].id == .identifier or ms.tokens[0].id == .extended_identifier);
1209 assert(ms.tokens[1].id == .l_paren);
1210
1211 var i: usize = 2;
1212 while (true) : (i += 1) {
1213 const token = ms.tokens[i];
1214 switch (token.id) {
1215 .r_paren => break,
1216 .comma => continue,
1217 .identifier, .extended_identifier => {
1218 const identifier = ms.slice(token);
1219 try hash.put(allocator, identifier, i);
1220 },
1221 else => return error.UnexpectedMacroToken,
1222 }
1223 }
1224 }
1225
1226 const Pattern = struct {
1227 tokens: []const CToken,
1228 source: []const u8,
1229 impl: []const u8,
1230 args_hash: ArgsPositionMap,
1231
1232 fn init(self: *Pattern, allocator: mem.Allocator, template: [2][]const u8) Error!void {
1233 const source = template[0];
1234 const impl = template[1];
1235
1236 var tok_list = std.ArrayList(CToken).init(allocator);
1237 defer tok_list.deinit();
1238 try tokenizeMacro(source, &tok_list);
1239 const tokens = try allocator.dupe(CToken, tok_list.items);
1240
1241 self.* = .{
1242 .tokens = tokens,
1243 .source = source,
1244 .impl = impl,
1245 .args_hash = .{},
1246 };
1247 const ms = MacroSlicer{ .source = source, .tokens = tokens };
1248 buildArgsHash(allocator, ms, &self.args_hash) catch |err| switch (err) {
1249 error.UnexpectedMacroToken => unreachable,
1250 else => |e| return e,
1251 };
1252 }
1253
1254 fn deinit(self: *Pattern, allocator: mem.Allocator) void {
1255 self.args_hash.deinit(allocator);
1256 allocator.free(self.tokens);
1257 }
1258
1259 /// This function assumes that `ms` has already been validated to contain a function-like
1260 /// macro, and that the parsed template macro in `self` also contains a function-like
1261 /// macro. Please review this logic carefully if changing that assumption. Two
1262 /// function-like macros are considered equivalent if and only if they contain the same
1263 /// list of tokens, modulo parameter names.
1264 pub fn isEquivalent(self: Pattern, ms: MacroSlicer, args_hash: ArgsPositionMap) bool {
1265 if (self.tokens.len != ms.tokens.len) return false;
1266 if (args_hash.count() != self.args_hash.count()) return false;
1267
1268 var i: usize = 2;
1269 while (self.tokens[i].id != .r_paren) : (i += 1) {}
1270
1271 const pattern_slicer = MacroSlicer{ .source = self.source, .tokens = self.tokens };
1272 while (i < self.tokens.len) : (i += 1) {
1273 const pattern_token = self.tokens[i];
1274 const macro_token = ms.tokens[i];
1275 if (pattern_token.id != macro_token.id) return false;
1276
1277 const pattern_bytes = pattern_slicer.slice(pattern_token);
1278 const macro_bytes = ms.slice(macro_token);
1279 switch (pattern_token.id) {
1280 .identifier, .extended_identifier => {
1281 const pattern_arg_index = self.args_hash.get(pattern_bytes);
1282 const macro_arg_index = args_hash.get(macro_bytes);
1283
1284 if (pattern_arg_index == null and macro_arg_index == null) {
1285 if (!mem.eql(u8, pattern_bytes, macro_bytes)) return false;
1286 } else if (pattern_arg_index != null and macro_arg_index != null) {
1287 if (pattern_arg_index.? != macro_arg_index.?) return false;
1288 } else {
1289 return false;
1290 }
1291 },
1292 .string_literal, .char_literal, .pp_num => {
1293 if (!mem.eql(u8, pattern_bytes, macro_bytes)) return false;
1294 },
1295 else => {
1296 // other tags correspond to keywords and operators that do not contain a "payload"
1297 // that can vary
1298 },
1299 }
1300 }
1301 return true;
1302 }
1303 };
1304
1305 pub fn init(allocator: mem.Allocator) Error!PatternList {
1306 const patterns = try allocator.alloc(Pattern, templates.len);
1307 for (templates, 0..) |template, i| {
1308 try patterns[i].init(allocator, template);
1309 }
1310 return PatternList{ .patterns = patterns };
1311 }
1312
1313 pub fn deinit(self: *PatternList, allocator: mem.Allocator) void {
1314 for (self.patterns) |*pattern| pattern.deinit(allocator);
1315 allocator.free(self.patterns);
1316 }
1317
1318 pub fn match(self: PatternList, allocator: mem.Allocator, ms: MacroSlicer) Error!?Pattern {
1319 var args_hash: ArgsPositionMap = .{};
1320 defer args_hash.deinit(allocator);
1321
1322 buildArgsHash(allocator, ms, &args_hash) catch |err| switch (err) {
1323 error.UnexpectedMacroToken => return null,
1324 else => |e| return e,
1325 };
1326
1327 for (self.patterns) |pattern| if (pattern.isEquivalent(ms, args_hash)) return pattern;
1328 return null;
1329 }
1330};
1331
1332pub const MacroSlicer = struct {
1333 source: []const u8,
1334 tokens: []const CToken,
1335
1336 pub fn slice(self: MacroSlicer, token: CToken) []const u8 {
1337 return self.source[token.start..token.end];
1338 }
1339};
1340
1341// Maps macro parameter names to token position, for determining if different
1342// identifiers refer to the same positional argument in different macros.
1343pub const ArgsPositionMap = std.StringArrayHashMapUnmanaged(usize);
1344
1345pub const Error = std.mem.Allocator.Error;
1346pub const MacroProcessingError = Error || error{UnexpectedMacroToken};
1347pub const TypeError = Error || error{UnsupportedType};
1348pub const TransError = TypeError || error{UnsupportedTranslation};
1349
1350pub const SymbolTable = std.StringArrayHashMap(ast.Node);
1351pub const AliasList = std.ArrayList(struct {
1352 alias: []const u8,
1353 name: []const u8,
1354});
1355
1356pub const ResultUsed = enum {
1357 used,
1358 unused,
1359};
1360
1361pub fn ScopeExtra(comptime ScopeExtraContext: type, comptime ScopeExtraType: type) type {
1362 return struct {
1363 id: Id,
1364 parent: ?*ScopeExtraScope,
1365
1366 const ScopeExtraScope = @This();
1367
1368 pub const Id = enum {
1369 block,
1370 root,
1371 condition,
1372 loop,
1373 do_loop,
1374 };
1375
1376 /// Used for the scope of condition expressions, for example `if (cond)`.
1377 /// The block is lazily initialised because it is only needed for rare
1378 /// cases of comma operators being used.
1379 pub const Condition = struct {
1380 base: ScopeExtraScope,
1381 block: ?Block = null,
1382
1383 pub fn getBlockScope(self: *Condition, c: *ScopeExtraContext) !*Block {
1384 if (self.block) |*b| return b;
1385 self.block = try Block.init(c, &self.base, true);
1386 return &self.block.?;
1387 }
1388
1389 pub fn deinit(self: *Condition) void {
1390 if (self.block) |*b| b.deinit();
1391 }
1392 };
1393
1394 /// Represents an in-progress Node.Block. This struct is stack-allocated.
1395 /// When it is deinitialized, it produces an Node.Block which is allocated
1396 /// into the main arena.
1397 pub const Block = struct {
1398 base: ScopeExtraScope,
1399 statements: std.ArrayList(ast.Node),
1400 variables: AliasList,
1401 mangle_count: u32 = 0,
1402 label: ?[]const u8 = null,
1403
1404 /// By default all variables are discarded, since we do not know in advance if they
1405 /// will be used. This maps the variable's name to the Discard payload, so that if
1406 /// the variable is subsequently referenced we can indicate that the discard should
1407 /// be skipped during the intermediate AST -> Zig AST render step.
1408 variable_discards: std.StringArrayHashMap(*ast.Payload.Discard),
1409
1410 /// When the block corresponds to a function, keep track of the return type
1411 /// so that the return expression can be cast, if necessary
1412 return_type: ?ScopeExtraType = null,
1413
1414 /// C static local variables are wrapped in a block-local struct. The struct
1415 /// is named after the (mangled) variable name, the Zig variable within the
1416 /// struct itself is given this name.
1417 pub const static_inner_name = "static";
1418
1419 /// C extern variables declared within a block are wrapped in a block-local
1420 /// struct. The struct is named ExternLocal_[variable_name], the Zig variable
1421 /// within the struct itself is [variable_name] by neccessity since it's an
1422 /// extern reference to an existing symbol.
1423 pub const extern_inner_prepend = "ExternLocal";
1424
1425 pub fn init(c: *ScopeExtraContext, parent: *ScopeExtraScope, labeled: bool) !Block {
1426 var blk = Block{
1427 .base = .{
1428 .id = .block,
1429 .parent = parent,
1430 },
1431 .statements = std.ArrayList(ast.Node).init(c.gpa),
1432 .variables = AliasList.init(c.gpa),
1433 .variable_discards = std.StringArrayHashMap(*ast.Payload.Discard).init(c.gpa),
1434 };
1435 if (labeled) {
1436 blk.label = try blk.makeMangledName(c, "blk");
1437 }
1438 return blk;
1439 }
1440
1441 pub fn deinit(self: *Block) void {
1442 self.statements.deinit();
1443 self.variables.deinit();
1444 self.variable_discards.deinit();
1445 self.* = undefined;
1446 }
1447
1448 pub fn complete(self: *Block, c: *ScopeExtraContext) !ast.Node {
1449 if (self.base.parent.?.id == .do_loop) {
1450 // We reserve 1 extra statement if the parent is a do_loop. This is in case of
1451 // do while, we want to put `if (cond) break;` at the end.
1452 const alloc_len = self.statements.items.len + @intFromBool(self.base.parent.?.id == .do_loop);
1453 var stmts = try c.arena.alloc(ast.Node, alloc_len);
1454 stmts.len = self.statements.items.len;
1455 @memcpy(stmts[0..self.statements.items.len], self.statements.items);
1456 return ast.Node.Tag.block.create(c.arena, .{
1457 .label = self.label,
1458 .stmts = stmts,
1459 });
1460 }
1461 if (self.statements.items.len == 0) return ast.Node.Tag.empty_block.init();
1462 return ast.Node.Tag.block.create(c.arena, .{
1463 .label = self.label,
1464 .stmts = try c.arena.dupe(ast.Node, self.statements.items),
1465 });
1466 }
1467
1468 /// Given the desired name, return a name that does not shadow anything from outer scopes.
1469 /// Inserts the returned name into the scope.
1470 /// The name will not be visible to callers of getAlias.
1471 pub fn reserveMangledName(scope: *Block, c: *ScopeExtraContext, name: []const u8) ![]const u8 {
1472 return scope.createMangledName(c, name, true);
1473 }
1474
1475 /// Same as reserveMangledName, but enables the alias immediately.
1476 pub fn makeMangledName(scope: *Block, c: *ScopeExtraContext, name: []const u8) ![]const u8 {
1477 return scope.createMangledName(c, name, false);
1478 }
1479
1480 pub fn createMangledName(scope: *Block, c: *ScopeExtraContext, name: []const u8, reservation: bool) ![]const u8 {
1481 const name_copy = try c.arena.dupe(u8, name);
1482 var proposed_name = name_copy;
1483 while (scope.contains(proposed_name)) {
1484 scope.mangle_count += 1;
1485 proposed_name = try std.fmt.allocPrint(c.arena, "{s}_{d}", .{ name, scope.mangle_count });
1486 }
1487 const new_mangle = try scope.variables.addOne();
1488 if (reservation) {
1489 new_mangle.* = .{ .name = name_copy, .alias = name_copy };
1490 } else {
1491 new_mangle.* = .{ .name = name_copy, .alias = proposed_name };
1492 }
1493 return proposed_name;
1494 }
1495
1496 pub fn getAlias(scope: *Block, name: []const u8) []const u8 {
1497 for (scope.variables.items) |p| {
1498 if (std.mem.eql(u8, p.name, name))
1499 return p.alias;
1500 }
1501 return scope.base.parent.?.getAlias(name);
1502 }
1503
1504 /// Finds the (potentially) mangled struct name for a locally scoped extern variable given the original declaration name.
1505 ///
1506 /// Block scoped extern declarations translate to:
1507 /// const MangledStructName = struct {extern [qualifiers] original_extern_variable_name: [type]};
1508 /// This finds MangledStructName given original_extern_variable_name for referencing correctly in transDeclRefExpr()
1509 pub fn getLocalExternAlias(scope: *Block, name: []const u8) ?[]const u8 {
1510 for (scope.statements.items) |node| {
1511 if (node.tag() == .extern_local_var) {
1512 const parent_node = node.castTag(.extern_local_var).?;
1513 const init_node = parent_node.data.init.castTag(.var_decl).?;
1514 if (std.mem.eql(u8, init_node.data.name, name)) {
1515 return parent_node.data.name;
1516 }
1517 }
1518 }
1519 return null;
1520 }
1521
1522 pub fn localContains(scope: *Block, name: []const u8) bool {
1523 for (scope.variables.items) |p| {
1524 if (std.mem.eql(u8, p.alias, name))
1525 return true;
1526 }
1527 return false;
1528 }
1529
1530 pub fn contains(scope: *Block, name: []const u8) bool {
1531 if (scope.localContains(name))
1532 return true;
1533 return scope.base.parent.?.contains(name);
1534 }
1535
1536 pub fn discardVariable(scope: *Block, c: *ScopeExtraContext, name: []const u8) Error!void {
1537 const name_node = try ast.Node.Tag.identifier.create(c.arena, name);
1538 const discard = try ast.Node.Tag.discard.create(c.arena, .{ .should_skip = false, .value = name_node });
1539 try scope.statements.append(discard);
1540 try scope.variable_discards.putNoClobber(name, discard.castTag(.discard).?);
1541 }
1542 };
1543
1544 pub const Root = struct {
1545 base: ScopeExtraScope,
1546 sym_table: SymbolTable,
1547 blank_macros: std.StringArrayHashMap(void),
1548 context: *ScopeExtraContext,
1549 nodes: std.ArrayList(ast.Node),
1550
1551 pub fn init(c: *ScopeExtraContext) Root {
1552 return .{
1553 .base = .{
1554 .id = .root,
1555 .parent = null,
1556 },
1557 .sym_table = SymbolTable.init(c.gpa),
1558 .blank_macros = std.StringArrayHashMap(void).init(c.gpa),
1559 .context = c,
1560 .nodes = std.ArrayList(ast.Node).init(c.gpa),
1561 };
1562 }
1563
1564 pub fn deinit(scope: *Root) void {
1565 scope.sym_table.deinit();
1566 scope.blank_macros.deinit();
1567 scope.nodes.deinit();
1568 }
1569
1570 /// Check if the global scope contains this name, without looking into the "future", e.g.
1571 /// ignore the preprocessed decl and macro names.
1572 pub fn containsNow(scope: *Root, name: []const u8) bool {
1573 return scope.sym_table.contains(name);
1574 }
1575
1576 /// Check if the global scope contains the name, includes all decls that haven't been translated yet.
1577 pub fn contains(scope: *Root, name: []const u8) bool {
1578 return scope.containsNow(name) or scope.context.global_names.contains(name) or scope.context.weak_global_names.contains(name);
1579 }
1580 };
1581
1582 pub fn findBlockScope(inner: *ScopeExtraScope, c: *ScopeExtraContext) !*Block {
1583 var scope = inner;
1584 while (true) {
1585 switch (scope.id) {
1586 .root => unreachable,
1587 .block => return @fieldParentPtr("base", scope),
1588 .condition => return @as(*Condition, @fieldParentPtr("base", scope)).getBlockScope(c),
1589 else => scope = scope.parent.?,
1590 }
1591 }
1592 }
1593
1594 pub fn findBlockReturnType(inner: *ScopeExtraScope) ScopeExtraType {
1595 var scope = inner;
1596 while (true) {
1597 switch (scope.id) {
1598 .root => unreachable,
1599 .block => {
1600 const block: *Block = @fieldParentPtr("base", scope);
1601 if (block.return_type) |ty| return ty;
1602 scope = scope.parent.?;
1603 },
1604 else => scope = scope.parent.?,
1605 }
1606 }
1607 }
1608
1609 pub fn getAlias(scope: *ScopeExtraScope, name: []const u8) []const u8 {
1610 return switch (scope.id) {
1611 .root => name,
1612 .block => @as(*Block, @fieldParentPtr("base", scope)).getAlias(name),
1613 .loop, .do_loop, .condition => scope.parent.?.getAlias(name),
1614 };
1615 }
1616
1617 pub fn getLocalExternAlias(scope: *ScopeExtraScope, name: []const u8) ?[]const u8 {
1618 return switch (scope.id) {
1619 .root => null,
1620 .block => ret: {
1621 const block = @as(*Block, @fieldParentPtr("base", scope));
1622 break :ret block.getLocalExternAlias(name);
1623 },
1624 .loop, .do_loop, .condition => scope.parent.?.getLocalExternAlias(name),
1625 };
1626 }
1627
1628 pub fn contains(scope: *ScopeExtraScope, name: []const u8) bool {
1629 return switch (scope.id) {
1630 .root => @as(*Root, @fieldParentPtr("base", scope)).contains(name),
1631 .block => @as(*Block, @fieldParentPtr("base", scope)).contains(name),
1632 .loop, .do_loop, .condition => scope.parent.?.contains(name),
1633 };
1634 }
1635
1636 pub fn getBreakableScope(inner: *ScopeExtraScope) *ScopeExtraScope {
1637 var scope = inner;
1638 while (true) {
1639 switch (scope.id) {
1640 .root => unreachable,
1641 .loop, .do_loop => return scope,
1642 else => scope = scope.parent.?,
1643 }
1644 }
1645 }
1646
1647 /// Appends a node to the first block scope if inside a function, or to the root tree if not.
1648 pub fn appendNode(inner: *ScopeExtraScope, node: ast.Node) !void {
1649 var scope = inner;
1650 while (true) {
1651 switch (scope.id) {
1652 .root => {
1653 const root: *Root = @fieldParentPtr("base", scope);
1654 return root.nodes.append(node);
1655 },
1656 .block => {
1657 const block: *Block = @fieldParentPtr("base", scope);
1658 return block.statements.append(node);
1659 },
1660 else => scope = scope.parent.?,
1661 }
1662 }
1663 }
1664
1665 pub fn skipVariableDiscard(inner: *ScopeExtraScope, name: []const u8) void {
1666 if (true) {
1667 // TODO: due to 'local variable is never mutated' errors, we can
1668 // only skip discards if a variable is used as an lvalue, which
1669 // we don't currently have detection for in translate-c.
1670 // Once #17584 is completed, perhaps we can do away with this
1671 // logic entirely, and instead rely on render to fixup code.
1672 return;
1673 }
1674 var scope = inner;
1675 while (true) {
1676 switch (scope.id) {
1677 .root => return,
1678 .block => {
1679 const block: *Block = @fieldParentPtr("base", scope);
1680 if (block.variable_discards.get(name)) |discard| {
1681 discard.data.should_skip = true;
1682 return;
1683 }
1684 },
1685 else => {},
1686 }
1687 scope = scope.parent.?;
1688 }
1689 }
1690 };
1691}
1692
1693pub fn tokenizeMacro(source: []const u8, tok_list: *std.ArrayList(CToken)) Error!void {
1694 var tokenizer: aro.Tokenizer = .{
1695 .buf = source,
1696 .source = .unused,
1697 .langopts = .{},
1698 };
1699 while (true) {
1700 const tok = tokenizer.next();
1701 switch (tok.id) {
1702 .whitespace => continue,
1703 .nl, .eof => {
1704 try tok_list.append(tok);
1705 break;
1706 },
1707 else => {},
1708 }
1709 try tok_list.append(tok);
1710 }
1711}
1712
1713// Testing here instead of test/translate_c.zig allows us to also test that the
1714// mapped function exists in `std.zig.c_translation.Macros`
1715test "Macro matching" {
1716 const testing = std.testing;
1717 const helper = struct {
1718 const MacroFunctions = std.zig.c_translation.Macros;
1719 fn checkMacro(allocator: mem.Allocator, pattern_list: PatternList, source: []const u8, comptime expected_match: ?[]const u8) !void {
1720 var tok_list = std.ArrayList(CToken).init(allocator);
1721 defer tok_list.deinit();
1722 try tokenizeMacro(source, &tok_list);
1723 const macro_slicer: MacroSlicer = .{ .source = source, .tokens = tok_list.items };
1724 const matched = try pattern_list.match(allocator, macro_slicer);
1725 if (expected_match) |expected| {
1726 try testing.expectEqualStrings(expected, matched.?.impl);
1727 try testing.expect(@hasDecl(MacroFunctions, expected));
1728 } else {
1729 try testing.expectEqual(@as(@TypeOf(matched), null), matched);
1730 }
1731 }
1732 };
1733 const allocator = std.testing.allocator;
1734 var pattern_list = try PatternList.init(allocator);
1735 defer pattern_list.deinit(allocator);
1736
1737 try helper.checkMacro(allocator, pattern_list, "BAR(Z) (Z ## F)", "F_SUFFIX");
1738 try helper.checkMacro(allocator, pattern_list, "BAR(Z) (Z ## U)", "U_SUFFIX");
1739 try helper.checkMacro(allocator, pattern_list, "BAR(Z) (Z ## L)", "L_SUFFIX");
1740 try helper.checkMacro(allocator, pattern_list, "BAR(Z) (Z ## LL)", "LL_SUFFIX");
1741 try helper.checkMacro(allocator, pattern_list, "BAR(Z) (Z ## UL)", "UL_SUFFIX");
1742 try helper.checkMacro(allocator, pattern_list, "BAR(Z) (Z ## ULL)", "ULL_SUFFIX");
1743 try helper.checkMacro(allocator, pattern_list,
1744 \\container_of(a, b, c) \
1745 \\(__typeof__(b))((char *)(a) - \
1746 \\ offsetof(__typeof__(*b), c))
1747 , "WL_CONTAINER_OF");
1748
1749 try helper.checkMacro(allocator, pattern_list, "NO_MATCH(X, Y) (X + Y)", null);
1750 try helper.checkMacro(allocator, pattern_list, "CAST_OR_CALL(X, Y) (X)(Y)", "CAST_OR_CALL");
1751 try helper.checkMacro(allocator, pattern_list, "CAST_OR_CALL(X, Y) ((X)(Y))", "CAST_OR_CALL");
1752 try helper.checkMacro(allocator, pattern_list, "IGNORE_ME(X) (void)(X)", "DISCARD");
1753 try helper.checkMacro(allocator, pattern_list, "IGNORE_ME(X) ((void)(X))", "DISCARD");
1754 try helper.checkMacro(allocator, pattern_list, "IGNORE_ME(X) (const void)(X)", "DISCARD");
1755 try helper.checkMacro(allocator, pattern_list, "IGNORE_ME(X) ((const void)(X))", "DISCARD");
1756 try helper.checkMacro(allocator, pattern_list, "IGNORE_ME(X) (volatile void)(X)", "DISCARD");
1757 try helper.checkMacro(allocator, pattern_list, "IGNORE_ME(X) ((volatile void)(X))", "DISCARD");
1758 try helper.checkMacro(allocator, pattern_list, "IGNORE_ME(X) (const volatile void)(X)", "DISCARD");
1759 try helper.checkMacro(allocator, pattern_list, "IGNORE_ME(X) ((const volatile void)(X))", "DISCARD");
1760 try helper.checkMacro(allocator, pattern_list, "IGNORE_ME(X) (volatile const void)(X)", "DISCARD");
1761 try helper.checkMacro(allocator, pattern_list, "IGNORE_ME(X) ((volatile const void)(X))", "DISCARD");
1762}
1763
1764/// Renders errors and fatal errors + associated notes (e.g. "expanded from here"); does not render warnings or associated notes
1765/// Terminates with exit code 1
1766fn renderErrorsAndExit(comp: *aro.Compilation) noreturn {
1767 defer std.process.exit(1);
1768
1769 var writer = aro.Diagnostics.defaultMsgWriter(std.io.tty.detectConfig(std.io.getStdErr()));
1770 defer writer.deinit(); // writer deinit must run *before* exit so that stderr is flushed
1771
1772 var saw_error = false;
1773 for (comp.diagnostics.list.items) |msg| {
1774 switch (msg.kind) {
1775 .@"error", .@"fatal error" => {
1776 saw_error = true;
1777 aro.Diagnostics.renderMessage(comp, &writer, msg);
1778 },
1779 .warning => saw_error = false,
1780 .note => {
1781 if (saw_error) {
1782 aro.Diagnostics.renderMessage(comp, &writer, msg);
1783 }
1784 },
1785 .off => {},
1786 .default => unreachable,
1787 }
1788 }
1789}
1790
1791pub fn main() !void {
1792 var arena_instance = std.heap.ArenaAllocator.init(std.heap.page_allocator);
1793 defer arena_instance.deinit();
1794 const arena = arena_instance.allocator();
1795
1796 var general_purpose_allocator: std.heap.GeneralPurposeAllocator(.{}) = .init;
1797 const gpa = general_purpose_allocator.allocator();
1798
1799 const args = try std.process.argsAlloc(arena);
1800
1801 var aro_comp = aro.Compilation.init(gpa, std.fs.cwd());
1802 defer aro_comp.deinit();
1803
1804 var tree = translate(gpa, &aro_comp, args) catch |err| switch (err) {
1805 error.ParsingFailed, error.FatalError => renderErrorsAndExit(&aro_comp),
1806 error.OutOfMemory => return error.OutOfMemory,
1807 error.StreamTooLong => std.zig.fatal("An input file was larger than 4GiB", .{}),
1808 };
1809 defer tree.deinit(gpa);
1810
1811 const formatted = try tree.render(arena);
1812 try std.io.getStdOut().writeAll(formatted);
1813 return std.process.cleanExit();
1814}
lib/compiler/aro_translate_c/ast.zig deleted-3027
...@@ -1,3027 +0,0 @@
1const std = @import("std");
2const Allocator = std.mem.Allocator;
3
4pub const Node = extern union {
5 /// If the tag value is less than Tag.no_payload_count, then no pointer
6 /// dereference is needed.
7 tag_if_small_enough: usize,
8 ptr_otherwise: *Payload,
9
10 pub const Tag = enum {
11 /// Declarations add themselves to the correct scopes and should not be emitted as this tag.
12 declaration,
13 null_literal,
14 undefined_literal,
15 /// opaque {}
16 opaque_literal,
17 true_literal,
18 false_literal,
19 empty_block,
20 return_void,
21 zero_literal,
22 one_literal,
23 void_type,
24 noreturn_type,
25 @"anytype",
26 @"continue",
27 @"break",
28 // After this, the tag requires a payload.
29
30 integer_literal,
31 float_literal,
32 string_literal,
33 char_literal,
34 enum_literal,
35 /// "string"[0..end]
36 string_slice,
37 identifier,
38 fn_identifier,
39 @"if",
40 /// if (!operand) break;
41 if_not_break,
42 @"while",
43 /// while (true) operand
44 while_true,
45 @"switch",
46 /// else => operand,
47 switch_else,
48 /// items => body,
49 switch_prong,
50 break_val,
51 @"return",
52 field_access,
53 array_access,
54 call,
55 var_decl,
56 /// const name = struct { init }
57 static_local_var,
58 /// const ExternLocal_name = struct { init }
59 extern_local_var,
60 /// var name = init.*
61 mut_str,
62 func,
63 warning,
64 @"struct",
65 @"union",
66 @"comptime",
67 @"defer",
68 array_init,
69 tuple,
70 container_init,
71 container_init_dot,
72 helpers_cast,
73 /// _ = operand;
74 discard,
75
76 // a + b
77 add,
78 // a = b
79 add_assign,
80 // c = (a = b)
81 add_wrap,
82 add_wrap_assign,
83 sub,
84 sub_assign,
85 sub_wrap,
86 sub_wrap_assign,
87 mul,
88 mul_assign,
89 mul_wrap,
90 mul_wrap_assign,
91 div,
92 div_assign,
93 shl,
94 shl_assign,
95 shr,
96 shr_assign,
97 mod,
98 mod_assign,
99 @"and",
100 @"or",
101 less_than,
102 less_than_equal,
103 greater_than,
104 greater_than_equal,
105 equal,
106 not_equal,
107 bit_and,
108 bit_and_assign,
109 bit_or,
110 bit_or_assign,
111 bit_xor,
112 bit_xor_assign,
113 array_cat,
114 ellipsis3,
115 assign,
116
117 /// @import("std").zig.c_builtins.<name>
118 import_c_builtin,
119 /// @intCast(operand)
120 int_cast,
121 /// @constCast(operand)
122 const_cast,
123 /// @volatileCast(operand)
124 volatile_cast,
125 /// @import("std").zig.c_translation.promoteIntLiteral(value, type, base)
126 helpers_promoteIntLiteral,
127 /// @import("std").zig.c_translation.signedRemainder(lhs, rhs)
128 signed_remainder,
129 /// @divTrunc(lhs, rhs)
130 div_trunc,
131 /// @intFromBool(operand)
132 int_from_bool,
133 /// @as(lhs, rhs)
134 as,
135 /// @truncate(operand)
136 truncate,
137 /// @bitCast(operand)
138 bit_cast,
139 /// @floatCast(operand)
140 float_cast,
141 /// @intFromFloat(operand)
142 int_from_float,
143 /// @floatFromInt(operand)
144 float_from_int,
145 /// @ptrFromInt(operand)
146 ptr_from_int,
147 /// @intFromPtr(operand)
148 int_from_ptr,
149 /// @alignCast(operand)
150 align_cast,
151 /// @ptrCast(operand)
152 ptr_cast,
153 /// @divExact(lhs, rhs)
154 div_exact,
155 /// @offsetOf(lhs, rhs)
156 offset_of,
157 /// @splat(operand)
158 vector_zero_init,
159 /// @shuffle(type, a, b, mask)
160 shuffle,
161 /// @extern(ty, .{ .name = n })
162 builtin_extern,
163
164 /// @import("std").zig.c_translation.MacroArithmetic.<op>(lhs, rhs)
165 macro_arithmetic,
166
167 asm_simple,
168
169 negate,
170 negate_wrap,
171 bit_not,
172 not,
173 address_of,
174 /// .?
175 unwrap,
176 /// .*
177 deref,
178
179 block,
180 /// { operand }
181 block_single,
182
183 sizeof,
184 alignof,
185 typeof,
186 typeinfo,
187 type,
188
189 optional_type,
190 c_pointer,
191 single_pointer,
192 array_type,
193 null_sentinel_array_type,
194
195 /// @import("std").zig.c_translation.sizeof(operand)
196 helpers_sizeof,
197 /// @import("std").zig.c_translation.FlexibleArrayType(lhs, rhs)
198 helpers_flexible_array_type,
199 /// @import("std").zig.c_translation.shuffleVectorIndex(lhs, rhs)
200 helpers_shuffle_vector_index,
201 /// @import("std").zig.c_translation.Macro.<operand>
202 helpers_macro,
203 /// @Vector(lhs, rhs)
204 vector,
205 /// @import("std").mem.zeroes(operand)
206 std_mem_zeroes,
207 /// @import("std").mem.zeroInit(lhs, rhs)
208 std_mem_zeroinit,
209 // pub const name = @compileError(msg);
210 fail_decl,
211 // var actual = mangled;
212 arg_redecl,
213 /// pub const alias = actual;
214 alias,
215 /// const name = init;
216 var_simple,
217 /// pub const name = init;
218 pub_var_simple,
219 /// pub? const name (: type)? = value
220 enum_constant,
221
222 /// pub inline fn name(params) return_type body
223 pub_inline_fn,
224
225 /// [0]type{}
226 empty_array,
227 /// [1]type{val} ** count
228 array_filler,
229
230 pub const last_no_payload_tag = Tag.@"break";
231 pub const no_payload_count = @intFromEnum(last_no_payload_tag) + 1;
232
233 pub fn Type(comptime t: Tag) type {
234 return switch (t) {
235 .declaration,
236 .null_literal,
237 .undefined_literal,
238 .opaque_literal,
239 .true_literal,
240 .false_literal,
241 .empty_block,
242 .return_void,
243 .zero_literal,
244 .one_literal,
245 .void_type,
246 .noreturn_type,
247 .@"anytype",
248 .@"continue",
249 .@"break",
250 => @compileError("Type Tag " ++ @tagName(t) ++ " has no payload"),
251
252 .std_mem_zeroes,
253 .@"return",
254 .@"comptime",
255 .@"defer",
256 .asm_simple,
257 .negate,
258 .negate_wrap,
259 .bit_not,
260 .not,
261 .optional_type,
262 .address_of,
263 .unwrap,
264 .deref,
265 .int_from_ptr,
266 .empty_array,
267 .while_true,
268 .if_not_break,
269 .switch_else,
270 .block_single,
271 .helpers_sizeof,
272 .int_from_bool,
273 .sizeof,
274 .alignof,
275 .typeof,
276 .typeinfo,
277 .align_cast,
278 .truncate,
279 .bit_cast,
280 .float_cast,
281 .int_from_float,
282 .float_from_int,
283 .ptr_from_int,
284 .ptr_cast,
285 .int_cast,
286 .const_cast,
287 .volatile_cast,
288 .vector_zero_init,
289 => Payload.UnOp,
290
291 .add,
292 .add_assign,
293 .add_wrap,
294 .add_wrap_assign,
295 .sub,
296 .sub_assign,
297 .sub_wrap,
298 .sub_wrap_assign,
299 .mul,
300 .mul_assign,
301 .mul_wrap,
302 .mul_wrap_assign,
303 .div,
304 .div_assign,
305 .shl,
306 .shl_assign,
307 .shr,
308 .shr_assign,
309 .mod,
310 .mod_assign,
311 .@"and",
312 .@"or",
313 .less_than,
314 .less_than_equal,
315 .greater_than,
316 .greater_than_equal,
317 .equal,
318 .not_equal,
319 .bit_and,
320 .bit_and_assign,
321 .bit_or,
322 .bit_or_assign,
323 .bit_xor,
324 .bit_xor_assign,
325 .div_trunc,
326 .signed_remainder,
327 .as,
328 .array_cat,
329 .ellipsis3,
330 .assign,
331 .array_access,
332 .std_mem_zeroinit,
333 .helpers_flexible_array_type,
334 .helpers_shuffle_vector_index,
335 .vector,
336 .div_exact,
337 .offset_of,
338 .helpers_cast,
339 => Payload.BinOp,
340
341 .integer_literal,
342 .float_literal,
343 .string_literal,
344 .char_literal,
345 .enum_literal,
346 .identifier,
347 .fn_identifier,
348 .warning,
349 .type,
350 .helpers_macro,
351 .import_c_builtin,
352 => Payload.Value,
353 .discard => Payload.Discard,
354 .@"if" => Payload.If,
355 .@"while" => Payload.While,
356 .@"switch", .array_init, .switch_prong => Payload.Switch,
357 .break_val => Payload.BreakVal,
358 .call => Payload.Call,
359 .var_decl => Payload.VarDecl,
360 .func => Payload.Func,
361 .@"struct", .@"union" => Payload.Record,
362 .tuple => Payload.TupleInit,
363 .container_init => Payload.ContainerInit,
364 .container_init_dot => Payload.ContainerInitDot,
365 .helpers_promoteIntLiteral => Payload.PromoteIntLiteral,
366 .block => Payload.Block,
367 .c_pointer, .single_pointer => Payload.Pointer,
368 .array_type, .null_sentinel_array_type => Payload.Array,
369 .arg_redecl, .alias, .fail_decl => Payload.ArgRedecl,
370 .var_simple, .pub_var_simple, .static_local_var, .extern_local_var, .mut_str => Payload.SimpleVarDecl,
371 .enum_constant => Payload.EnumConstant,
372 .array_filler => Payload.ArrayFiller,
373 .pub_inline_fn => Payload.PubInlineFn,
374 .field_access => Payload.FieldAccess,
375 .string_slice => Payload.StringSlice,
376 .shuffle => Payload.Shuffle,
377 .builtin_extern => Payload.Extern,
378 .macro_arithmetic => Payload.MacroArithmetic,
379 };
380 }
381
382 pub fn init(comptime t: Tag) Node {
383 comptime std.debug.assert(@intFromEnum(t) < Tag.no_payload_count);
384 return .{ .tag_if_small_enough = @intFromEnum(t) };
385 }
386
387 pub fn create(comptime t: Tag, ally: Allocator, data: Data(t)) error{OutOfMemory}!Node {
388 const ptr = try ally.create(t.Type());
389 ptr.* = .{
390 .base = .{ .tag = t },
391 .data = data,
392 };
393 return Node{ .ptr_otherwise = &ptr.base };
394 }
395
396 pub fn Data(comptime t: Tag) type {
397 return std.meta.fieldInfo(t.Type(), .data).type;
398 }
399 };
400
401 pub fn tag(self: Node) Tag {
402 if (self.tag_if_small_enough < Tag.no_payload_count) {
403 return @as(Tag, @enumFromInt(@as(std.meta.Tag(Tag), @intCast(self.tag_if_small_enough))));
404 } else {
405 return self.ptr_otherwise.tag;
406 }
407 }
408
409 pub fn castTag(self: Node, comptime t: Tag) ?*t.Type() {
410 if (self.tag_if_small_enough < Tag.no_payload_count)
411 return null;
412
413 if (self.ptr_otherwise.tag == t)
414 return @alignCast(@fieldParentPtr("base", self.ptr_otherwise));
415
416 return null;
417 }
418
419 pub fn initPayload(payload: *Payload) Node {
420 std.debug.assert(@intFromEnum(payload.tag) >= Tag.no_payload_count);
421 return .{ .ptr_otherwise = payload };
422 }
423
424 pub fn isNoreturn(node: Node, break_counts: bool) bool {
425 switch (node.tag()) {
426 .block => {
427 const block_node = node.castTag(.block).?;
428 if (block_node.data.stmts.len == 0) return false;
429
430 const last = block_node.data.stmts[block_node.data.stmts.len - 1];
431 return last.isNoreturn(break_counts);
432 },
433 .@"switch" => {
434 const switch_node = node.castTag(.@"switch").?;
435
436 for (switch_node.data.cases) |case| {
437 const body = if (case.castTag(.switch_else)) |some|
438 some.data
439 else if (case.castTag(.switch_prong)) |some|
440 some.data.cond
441 else
442 unreachable;
443
444 if (!body.isNoreturn(break_counts)) return false;
445 }
446 return true;
447 },
448 .@"return", .return_void => return true,
449 .@"break" => if (break_counts) return true,
450 else => {},
451 }
452 return false;
453 }
454};
455
456pub const Payload = struct {
457 tag: Node.Tag,
458
459 pub const Value = struct {
460 base: Payload,
461 data: []const u8,
462 };
463
464 pub const UnOp = struct {
465 base: Payload,
466 data: Node,
467 };
468
469 pub const BinOp = struct {
470 base: Payload,
471 data: struct {
472 lhs: Node,
473 rhs: Node,
474 },
475 };
476
477 pub const Discard = struct {
478 base: Payload,
479 data: struct {
480 should_skip: bool,
481 value: Node,
482 },
483 };
484
485 pub const If = struct {
486 base: Payload,
487 data: struct {
488 cond: Node,
489 then: Node,
490 @"else": ?Node,
491 },
492 };
493
494 pub const While = struct {
495 base: Payload,
496 data: struct {
497 cond: Node,
498 body: Node,
499 cont_expr: ?Node,
500 },
501 };
502
503 pub const Switch = struct {
504 base: Payload,
505 data: struct {
506 cond: Node,
507 cases: []Node,
508 },
509 };
510
511 pub const BreakVal = struct {
512 base: Payload,
513 data: struct {
514 label: ?[]const u8,
515 val: Node,
516 },
517 };
518
519 pub const Call = struct {
520 base: Payload,
521 data: struct {
522 lhs: Node,
523 args: []Node,
524 },
525 };
526
527 pub const VarDecl = struct {
528 base: Payload,
529 data: struct {
530 is_pub: bool,
531 is_const: bool,
532 is_extern: bool,
533 is_export: bool,
534 is_threadlocal: bool,
535 alignment: ?c_uint,
536 linksection_string: ?[]const u8,
537 name: []const u8,
538 type: Node,
539 init: ?Node,
540 },
541 };
542
543 pub const Func = struct {
544 base: Payload,
545 data: struct {
546 is_pub: bool,
547 is_extern: bool,
548 is_export: bool,
549 is_inline: bool,
550 is_var_args: bool,
551 name: ?[]const u8,
552 linksection_string: ?[]const u8,
553 explicit_callconv: ?CallingConvention,
554 params: []Param,
555 return_type: Node,
556 body: ?Node,
557 alignment: ?c_uint,
558 },
559
560 pub const CallingConvention = enum {
561 c,
562 x86_64_sysv,
563 x86_64_win,
564 x86_stdcall,
565 x86_fastcall,
566 x86_thiscall,
567 x86_vectorcall,
568 aarch64_vfabi,
569 arm_aapcs,
570 arm_aapcs_vfp,
571 m68k_rtd,
572 };
573 };
574
575 pub const Param = struct {
576 is_noalias: bool,
577 name: ?[]const u8,
578 type: Node,
579 };
580
581 pub const Record = struct {
582 base: Payload,
583 data: struct {
584 layout: enum { @"packed", @"extern", none },
585 fields: []Field,
586 functions: []Node,
587 variables: []Node,
588 },
589
590 pub const Field = struct {
591 name: []const u8,
592 type: Node,
593 alignment: ?c_uint,
594 default_value: ?Node,
595 };
596 };
597
598 pub const TupleInit = struct {
599 base: Payload,
600 data: []Node,
601 };
602
603 pub const ContainerInit = struct {
604 base: Payload,
605 data: struct {
606 lhs: Node,
607 inits: []Initializer,
608 },
609
610 pub const Initializer = struct {
611 name: []const u8,
612 value: Node,
613 };
614 };
615
616 pub const ContainerInitDot = struct {
617 base: Payload,
618 data: []Initializer,
619
620 pub const Initializer = struct {
621 name: []const u8,
622 value: Node,
623 };
624 };
625
626 pub const Block = struct {
627 base: Payload,
628 data: struct {
629 label: ?[]const u8,
630 stmts: []Node,
631 },
632 };
633
634 pub const Array = struct {
635 base: Payload,
636 data: ArrayTypeInfo,
637
638 pub const ArrayTypeInfo = struct {
639 elem_type: Node,
640 len: usize,
641 };
642 };
643
644 pub const Pointer = struct {
645 base: Payload,
646 data: struct {
647 elem_type: Node,
648 is_const: bool,
649 is_volatile: bool,
650 },
651 };
652
653 pub const ArgRedecl = struct {
654 base: Payload,
655 data: struct {
656 actual: []const u8,
657 mangled: []const u8,
658 },
659 };
660
661 pub const SimpleVarDecl = struct {
662 base: Payload,
663 data: struct {
664 name: []const u8,
665 init: Node,
666 },
667 };
668
669 pub const EnumConstant = struct {
670 base: Payload,
671 data: struct {
672 name: []const u8,
673 is_public: bool,
674 type: ?Node,
675 value: Node,
676 },
677 };
678
679 pub const ArrayFiller = struct {
680 base: Payload,
681 data: struct {
682 type: Node,
683 filler: Node,
684 count: usize,
685 },
686 };
687
688 pub const PubInlineFn = struct {
689 base: Payload,
690 data: struct {
691 name: []const u8,
692 params: []Param,
693 return_type: Node,
694 body: Node,
695 },
696 };
697
698 pub const FieldAccess = struct {
699 base: Payload,
700 data: struct {
701 lhs: Node,
702 field_name: []const u8,
703 },
704 };
705
706 pub const PromoteIntLiteral = struct {
707 base: Payload,
708 data: struct {
709 value: Node,
710 type: Node,
711 base: Node,
712 },
713 };
714
715 pub const StringSlice = struct {
716 base: Payload,
717 data: struct {
718 string: Node,
719 end: usize,
720 },
721 };
722
723 pub const Shuffle = struct {
724 base: Payload,
725 data: struct {
726 element_type: Node,
727 a: Node,
728 b: Node,
729 mask_vector: Node,
730 },
731 };
732
733 pub const Extern = struct {
734 base: Payload,
735 data: struct {
736 type: Node,
737 name: Node,
738 },
739 };
740
741 pub const MacroArithmetic = struct {
742 base: Payload,
743 data: struct {
744 op: Operator,
745 lhs: Node,
746 rhs: Node,
747 },
748
749 pub const Operator = enum { div, rem };
750 };
751};
752
753/// Converts the nodes into a Zig Ast.
754/// Caller must free the source slice.
755pub fn render(gpa: Allocator, nodes: []const Node) !std.zig.Ast {
756 var ctx = Context{
757 .gpa = gpa,
758 .buf = std.ArrayList(u8).init(gpa),
759 };
760 defer ctx.buf.deinit();
761 defer ctx.nodes.deinit(gpa);
762 defer ctx.extra_data.deinit(gpa);
763 defer ctx.tokens.deinit(gpa);
764
765 // Estimate that each top level node has 10 child nodes.
766 const estimated_node_count = nodes.len * 10;
767 try ctx.nodes.ensureTotalCapacity(gpa, estimated_node_count);
768 // Estimate that each each node has 2 tokens.
769 const estimated_tokens_count = estimated_node_count * 2;
770 try ctx.tokens.ensureTotalCapacity(gpa, estimated_tokens_count);
771 // Estimate that each each token is 3 bytes long.
772 const estimated_buf_len = estimated_tokens_count * 3;
773 try ctx.buf.ensureTotalCapacity(estimated_buf_len);
774
775 ctx.nodes.appendAssumeCapacity(.{
776 .tag = .root,
777 .main_token = 0,
778 .data = .{
779 .lhs = undefined,
780 .rhs = undefined,
781 },
782 });
783
784 const root_members = blk: {
785 var result = std.ArrayList(NodeIndex).init(gpa);
786 defer result.deinit();
787
788 for (nodes) |node| {
789 const res = try renderNode(&ctx, node);
790 if (node.tag() == .warning) continue;
791 try result.append(res);
792 }
793 break :blk try ctx.listToSpan(result.items);
794 };
795
796 ctx.nodes.items(.data)[0] = .{
797 .lhs = root_members.start,
798 .rhs = root_members.end,
799 };
800
801 try ctx.tokens.append(gpa, .{
802 .tag = .eof,
803 .start = @as(u32, @intCast(ctx.buf.items.len)),
804 });
805
806 return std.zig.Ast{
807 .source = try ctx.buf.toOwnedSliceSentinel(0),
808 .tokens = ctx.tokens.toOwnedSlice(),
809 .nodes = ctx.nodes.toOwnedSlice(),
810 .extra_data = try ctx.extra_data.toOwnedSlice(gpa),
811 .errors = &.{},
812 .mode = .zig,
813 };
814}
815
816const NodeIndex = std.zig.Ast.Node.Index;
817const NodeSubRange = std.zig.Ast.Node.SubRange;
818const TokenIndex = std.zig.Ast.TokenIndex;
819const TokenTag = std.zig.Token.Tag;
820
821const Context = struct {
822 gpa: Allocator,
823 buf: std.ArrayList(u8),
824 nodes: std.zig.Ast.NodeList = .{},
825 extra_data: std.ArrayListUnmanaged(std.zig.Ast.Node.Index) = .empty,
826 tokens: std.zig.Ast.TokenList = .{},
827
828 fn addTokenFmt(c: *Context, tag: TokenTag, comptime format: []const u8, args: anytype) Allocator.Error!TokenIndex {
829 const start_index = c.buf.items.len;
830 try c.buf.writer().print(format ++ " ", args);
831
832 try c.tokens.append(c.gpa, .{
833 .tag = tag,
834 .start = @as(u32, @intCast(start_index)),
835 });
836
837 return @as(u32, @intCast(c.tokens.len - 1));
838 }
839
840 fn addToken(c: *Context, tag: TokenTag, bytes: []const u8) Allocator.Error!TokenIndex {
841 return c.addTokenFmt(tag, "{s}", .{bytes});
842 }
843
844 fn addIdentifier(c: *Context, bytes: []const u8) Allocator.Error!TokenIndex {
845 if (std.zig.primitives.isPrimitive(bytes))
846 return c.addTokenFmt(.identifier, "@\"{s}\"", .{bytes});
847 return c.addTokenFmt(.identifier, "{p}", .{std.zig.fmtId(bytes)});
848 }
849
850 fn listToSpan(c: *Context, list: []const NodeIndex) Allocator.Error!NodeSubRange {
851 try c.extra_data.appendSlice(c.gpa, list);
852 return NodeSubRange{
853 .start = @as(NodeIndex, @intCast(c.extra_data.items.len - list.len)),
854 .end = @as(NodeIndex, @intCast(c.extra_data.items.len)),
855 };
856 }
857
858 fn addNode(c: *Context, elem: std.zig.Ast.Node) Allocator.Error!NodeIndex {
859 const result = @as(NodeIndex, @intCast(c.nodes.len));
860 try c.nodes.append(c.gpa, elem);
861 return result;
862 }
863
864 fn addExtra(c: *Context, extra: anytype) Allocator.Error!NodeIndex {
865 const fields = std.meta.fields(@TypeOf(extra));
866 try c.extra_data.ensureUnusedCapacity(c.gpa, fields.len);
867 const result = @as(u32, @intCast(c.extra_data.items.len));
868 inline for (fields) |field| {
869 comptime std.debug.assert(field.type == NodeIndex);
870 c.extra_data.appendAssumeCapacity(@field(extra, field.name));
871 }
872 return result;
873 }
874};
875
876fn renderNodes(c: *Context, nodes: []const Node) Allocator.Error!NodeSubRange {
877 var result = std.ArrayList(NodeIndex).init(c.gpa);
878 defer result.deinit();
879
880 for (nodes) |node| {
881 const res = try renderNode(c, node);
882 if (node.tag() == .warning) continue;
883 try result.append(res);
884 }
885
886 return try c.listToSpan(result.items);
887}
888
889fn renderNode(c: *Context, node: Node) Allocator.Error!NodeIndex {
890 switch (node.tag()) {
891 .declaration => unreachable,
892 .warning => {
893 const payload = node.castTag(.warning).?.data;
894 try c.buf.append('\n');
895 try c.buf.appendSlice(payload);
896 try c.buf.append('\n');
897 return @as(NodeIndex, 0); // error: integer value 0 cannot be coerced to type 'std.mem.Allocator.Error!u32'
898 },
899 .helpers_cast => {
900 const payload = node.castTag(.helpers_cast).?.data;
901 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "cast" });
902 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
903 },
904 .helpers_promoteIntLiteral => {
905 const payload = node.castTag(.helpers_promoteIntLiteral).?.data;
906 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "promoteIntLiteral" });
907 return renderCall(c, import_node, &.{ payload.type, payload.value, payload.base });
908 },
909 .helpers_sizeof => {
910 const payload = node.castTag(.helpers_sizeof).?.data;
911 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "sizeof" });
912 return renderCall(c, import_node, &.{payload});
913 },
914 .std_mem_zeroes => {
915 const payload = node.castTag(.std_mem_zeroes).?.data;
916 const import_node = try renderStdImport(c, &.{ "mem", "zeroes" });
917 return renderCall(c, import_node, &.{payload});
918 },
919 .std_mem_zeroinit => {
920 const payload = node.castTag(.std_mem_zeroinit).?.data;
921 const import_node = try renderStdImport(c, &.{ "mem", "zeroInit" });
922 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
923 },
924 .helpers_flexible_array_type => {
925 const payload = node.castTag(.helpers_flexible_array_type).?.data;
926 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "FlexibleArrayType" });
927 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
928 },
929 .helpers_shuffle_vector_index => {
930 const payload = node.castTag(.helpers_shuffle_vector_index).?.data;
931 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "shuffleVectorIndex" });
932 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
933 },
934 .vector => {
935 const payload = node.castTag(.vector).?.data;
936 return renderBuiltinCall(c, "@Vector", &.{ payload.lhs, payload.rhs });
937 },
938 .call => {
939 const payload = node.castTag(.call).?.data;
940 // Cosmetic: avoids an unnecesary address_of on most function calls.
941 const lhs = if (payload.lhs.tag() == .fn_identifier)
942 try c.addNode(.{
943 .tag = .identifier,
944 .main_token = try c.addIdentifier(payload.lhs.castTag(.fn_identifier).?.data),
945 .data = undefined,
946 })
947 else
948 try renderNodeGrouped(c, payload.lhs);
949 return renderCall(c, lhs, payload.args);
950 },
951 .null_literal => return c.addNode(.{
952 .tag = .identifier,
953 .main_token = try c.addToken(.identifier, "null"),
954 .data = undefined,
955 }),
956 .undefined_literal => return c.addNode(.{
957 .tag = .identifier,
958 .main_token = try c.addToken(.identifier, "undefined"),
959 .data = undefined,
960 }),
961 .true_literal => return c.addNode(.{
962 .tag = .identifier,
963 .main_token = try c.addToken(.identifier, "true"),
964 .data = undefined,
965 }),
966 .false_literal => return c.addNode(.{
967 .tag = .identifier,
968 .main_token = try c.addToken(.identifier, "false"),
969 .data = undefined,
970 }),
971 .zero_literal => return c.addNode(.{
972 .tag = .number_literal,
973 .main_token = try c.addToken(.number_literal, "0"),
974 .data = undefined,
975 }),
976 .one_literal => return c.addNode(.{
977 .tag = .number_literal,
978 .main_token = try c.addToken(.number_literal, "1"),
979 .data = undefined,
980 }),
981 .void_type => return c.addNode(.{
982 .tag = .identifier,
983 .main_token = try c.addToken(.identifier, "void"),
984 .data = undefined,
985 }),
986 .noreturn_type => return c.addNode(.{
987 .tag = .identifier,
988 .main_token = try c.addToken(.identifier, "noreturn"),
989 .data = undefined,
990 }),
991 .@"continue" => return c.addNode(.{
992 .tag = .@"continue",
993 .main_token = try c.addToken(.keyword_continue, "continue"),
994 .data = .{
995 .lhs = 0,
996 .rhs = undefined,
997 },
998 }),
999 .return_void => return c.addNode(.{
1000 .tag = .@"return",
1001 .main_token = try c.addToken(.keyword_return, "return"),
1002 .data = .{
1003 .lhs = 0,
1004 .rhs = undefined,
1005 },
1006 }),
1007 .@"break" => return c.addNode(.{
1008 .tag = .@"break",
1009 .main_token = try c.addToken(.keyword_break, "break"),
1010 .data = .{
1011 .lhs = 0,
1012 .rhs = 0,
1013 },
1014 }),
1015 .break_val => {
1016 const payload = node.castTag(.break_val).?.data;
1017 const tok = try c.addToken(.keyword_break, "break");
1018 const break_label = if (payload.label) |some| blk: {
1019 _ = try c.addToken(.colon, ":");
1020 break :blk try c.addIdentifier(some);
1021 } else 0;
1022 return c.addNode(.{
1023 .tag = .@"break",
1024 .main_token = tok,
1025 .data = .{
1026 .lhs = break_label,
1027 .rhs = try renderNode(c, payload.val),
1028 },
1029 });
1030 },
1031 .@"return" => {
1032 const payload = node.castTag(.@"return").?.data;
1033 return c.addNode(.{
1034 .tag = .@"return",
1035 .main_token = try c.addToken(.keyword_return, "return"),
1036 .data = .{
1037 .lhs = try renderNode(c, payload),
1038 .rhs = undefined,
1039 },
1040 });
1041 },
1042 .@"comptime" => {
1043 const payload = node.castTag(.@"comptime").?.data;
1044 return c.addNode(.{
1045 .tag = .@"comptime",
1046 .main_token = try c.addToken(.keyword_comptime, "comptime"),
1047 .data = .{
1048 .lhs = try renderNode(c, payload),
1049 .rhs = undefined,
1050 },
1051 });
1052 },
1053 .@"defer" => {
1054 const payload = node.castTag(.@"defer").?.data;
1055 return c.addNode(.{
1056 .tag = .@"defer",
1057 .main_token = try c.addToken(.keyword_defer, "defer"),
1058 .data = .{
1059 .lhs = undefined,
1060 .rhs = try renderNode(c, payload),
1061 },
1062 });
1063 },
1064 .asm_simple => {
1065 const payload = node.castTag(.asm_simple).?.data;
1066 const asm_token = try c.addToken(.keyword_asm, "asm");
1067 _ = try c.addToken(.l_paren, "(");
1068 return c.addNode(.{
1069 .tag = .asm_simple,
1070 .main_token = asm_token,
1071 .data = .{
1072 .lhs = try renderNode(c, payload),
1073 .rhs = try c.addToken(.r_paren, ")"),
1074 },
1075 });
1076 },
1077 .type => {
1078 const payload = node.castTag(.type).?.data;
1079 return c.addNode(.{
1080 .tag = .identifier,
1081 .main_token = try c.addToken(.identifier, payload),
1082 .data = undefined,
1083 });
1084 },
1085 .identifier => {
1086 const payload = node.castTag(.identifier).?.data;
1087 return c.addNode(.{
1088 .tag = .identifier,
1089 .main_token = try c.addIdentifier(payload),
1090 .data = undefined,
1091 });
1092 },
1093 .fn_identifier => {
1094 // C semantics are that a function identifier has address
1095 // value (implicit in stage1, explicit in stage2), except in
1096 // the context of an address_of, which is handled there.
1097 const payload = node.castTag(.fn_identifier).?.data;
1098 const tok = try c.addToken(.ampersand, "&");
1099 const arg = try c.addNode(.{
1100 .tag = .identifier,
1101 .main_token = try c.addIdentifier(payload),
1102 .data = undefined,
1103 });
1104 return c.addNode(.{
1105 .tag = .address_of,
1106 .main_token = tok,
1107 .data = .{
1108 .lhs = arg,
1109 .rhs = undefined,
1110 },
1111 });
1112 },
1113 .float_literal => {
1114 const payload = node.castTag(.float_literal).?.data;
1115 return c.addNode(.{
1116 .tag = .number_literal,
1117 .main_token = try c.addToken(.number_literal, payload),
1118 .data = undefined,
1119 });
1120 },
1121 .integer_literal => {
1122 const payload = node.castTag(.integer_literal).?.data;
1123 return c.addNode(.{
1124 .tag = .number_literal,
1125 .main_token = try c.addToken(.number_literal, payload),
1126 .data = undefined,
1127 });
1128 },
1129 .string_literal => {
1130 const payload = node.castTag(.string_literal).?.data;
1131 return c.addNode(.{
1132 .tag = .string_literal,
1133 .main_token = try c.addToken(.string_literal, payload),
1134 .data = undefined,
1135 });
1136 },
1137 .char_literal => {
1138 const payload = node.castTag(.char_literal).?.data;
1139 return c.addNode(.{
1140 .tag = .char_literal,
1141 .main_token = try c.addToken(.char_literal, payload),
1142 .data = undefined,
1143 });
1144 },
1145 .enum_literal => {
1146 const payload = node.castTag(.enum_literal).?.data;
1147 _ = try c.addToken(.period, ".");
1148 return c.addNode(.{
1149 .tag = .enum_literal,
1150 .main_token = try c.addToken(.identifier, payload),
1151 .data = undefined,
1152 });
1153 },
1154 .helpers_macro => {
1155 const payload = node.castTag(.helpers_macro).?.data;
1156 const chain = [_][]const u8{
1157 "zig",
1158 "c_translation",
1159 "Macros",
1160 payload,
1161 };
1162 return renderStdImport(c, &chain);
1163 },
1164 .import_c_builtin => {
1165 const payload = node.castTag(.import_c_builtin).?.data;
1166 const chain = [_][]const u8{
1167 "zig",
1168 "c_builtins",
1169 payload,
1170 };
1171 return renderStdImport(c, &chain);
1172 },
1173 .string_slice => {
1174 const payload = node.castTag(.string_slice).?.data;
1175
1176 const string = try renderNode(c, payload.string);
1177 const l_bracket = try c.addToken(.l_bracket, "[");
1178 const start = try c.addNode(.{
1179 .tag = .number_literal,
1180 .main_token = try c.addToken(.number_literal, "0"),
1181 .data = undefined,
1182 });
1183 _ = try c.addToken(.ellipsis2, "..");
1184 const end = try c.addNode(.{
1185 .tag = .number_literal,
1186 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{payload.end}),
1187 .data = undefined,
1188 });
1189 _ = try c.addToken(.r_bracket, "]");
1190
1191 return c.addNode(.{
1192 .tag = .slice,
1193 .main_token = l_bracket,
1194 .data = .{
1195 .lhs = string,
1196 .rhs = try c.addExtra(std.zig.Ast.Node.Slice{
1197 .start = start,
1198 .end = end,
1199 }),
1200 },
1201 });
1202 },
1203 .fail_decl => {
1204 const payload = node.castTag(.fail_decl).?.data;
1205 // pub const name = @compileError(msg);
1206 _ = try c.addToken(.keyword_pub, "pub");
1207 const const_tok = try c.addToken(.keyword_const, "const");
1208 _ = try c.addIdentifier(payload.actual);
1209 _ = try c.addToken(.equal, "=");
1210
1211 const compile_error_tok = try c.addToken(.builtin, "@compileError");
1212 _ = try c.addToken(.l_paren, "(");
1213 const err_msg_tok = try c.addTokenFmt(.string_literal, "\"{}\"", .{std.zig.fmtEscapes(payload.mangled)});
1214 const err_msg = try c.addNode(.{
1215 .tag = .string_literal,
1216 .main_token = err_msg_tok,
1217 .data = undefined,
1218 });
1219 _ = try c.addToken(.r_paren, ")");
1220 const compile_error = try c.addNode(.{
1221 .tag = .builtin_call_two,
1222 .main_token = compile_error_tok,
1223 .data = .{
1224 .lhs = err_msg,
1225 .rhs = 0,
1226 },
1227 });
1228 _ = try c.addToken(.semicolon, ";");
1229
1230 return c.addNode(.{
1231 .tag = .simple_var_decl,
1232 .main_token = const_tok,
1233 .data = .{
1234 .lhs = 0,
1235 .rhs = compile_error,
1236 },
1237 });
1238 },
1239 .pub_var_simple, .var_simple => {
1240 const payload = @as(*Payload.SimpleVarDecl, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
1241 if (node.tag() == .pub_var_simple) _ = try c.addToken(.keyword_pub, "pub");
1242 const const_tok = try c.addToken(.keyword_const, "const");
1243 _ = try c.addIdentifier(payload.name);
1244 _ = try c.addToken(.equal, "=");
1245
1246 const init = try renderNode(c, payload.init);
1247 _ = try c.addToken(.semicolon, ";");
1248
1249 return c.addNode(.{
1250 .tag = .simple_var_decl,
1251 .main_token = const_tok,
1252 .data = .{
1253 .lhs = 0,
1254 .rhs = init,
1255 },
1256 });
1257 },
1258 .static_local_var => {
1259 const payload = node.castTag(.static_local_var).?.data;
1260
1261 const const_tok = try c.addToken(.keyword_const, "const");
1262 _ = try c.addIdentifier(payload.name);
1263 _ = try c.addToken(.equal, "=");
1264
1265 const kind_tok = try c.addToken(.keyword_struct, "struct");
1266 _ = try c.addToken(.l_brace, "{");
1267
1268 const container_def = try c.addNode(.{
1269 .tag = .container_decl_two_trailing,
1270 .main_token = kind_tok,
1271 .data = .{
1272 .lhs = try renderNode(c, payload.init),
1273 .rhs = 0,
1274 },
1275 });
1276 _ = try c.addToken(.r_brace, "}");
1277 _ = try c.addToken(.semicolon, ";");
1278
1279 return c.addNode(.{
1280 .tag = .simple_var_decl,
1281 .main_token = const_tok,
1282 .data = .{
1283 .lhs = 0,
1284 .rhs = container_def,
1285 },
1286 });
1287 },
1288 .extern_local_var => {
1289 const payload = node.castTag(.extern_local_var).?.data;
1290
1291 const const_tok = try c.addToken(.keyword_const, "const");
1292 _ = try c.addIdentifier(payload.name);
1293 _ = try c.addToken(.equal, "=");
1294
1295 const kind_tok = try c.addToken(.keyword_struct, "struct");
1296 _ = try c.addToken(.l_brace, "{");
1297
1298 const container_def = try c.addNode(.{
1299 .tag = .container_decl_two_trailing,
1300 .main_token = kind_tok,
1301 .data = .{
1302 .lhs = try renderNode(c, payload.init),
1303 .rhs = 0,
1304 },
1305 });
1306 _ = try c.addToken(.r_brace, "}");
1307 _ = try c.addToken(.semicolon, ";");
1308
1309 return c.addNode(.{
1310 .tag = .simple_var_decl,
1311 .main_token = const_tok,
1312 .data = .{
1313 .lhs = 0,
1314 .rhs = container_def,
1315 },
1316 });
1317 },
1318 .mut_str => {
1319 const payload = node.castTag(.mut_str).?.data;
1320
1321 const var_tok = try c.addToken(.keyword_var, "var");
1322 _ = try c.addIdentifier(payload.name);
1323 _ = try c.addToken(.equal, "=");
1324
1325 const deref = try c.addNode(.{
1326 .tag = .deref,
1327 .data = .{
1328 .lhs = try renderNodeGrouped(c, payload.init),
1329 .rhs = undefined,
1330 },
1331 .main_token = try c.addToken(.period_asterisk, ".*"),
1332 });
1333 _ = try c.addToken(.semicolon, ";");
1334
1335 return c.addNode(.{
1336 .tag = .simple_var_decl,
1337 .main_token = var_tok,
1338 .data = .{ .lhs = 0, .rhs = deref },
1339 });
1340 },
1341 .var_decl => return renderVar(c, node),
1342 .arg_redecl, .alias => {
1343 const payload = @as(*Payload.ArgRedecl, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
1344 if (node.tag() == .alias) _ = try c.addToken(.keyword_pub, "pub");
1345 const mut_tok = if (node.tag() == .alias)
1346 try c.addToken(.keyword_const, "const")
1347 else
1348 try c.addToken(.keyword_var, "var");
1349 _ = try c.addIdentifier(payload.actual);
1350 _ = try c.addToken(.equal, "=");
1351
1352 const init = try c.addNode(.{
1353 .tag = .identifier,
1354 .main_token = try c.addIdentifier(payload.mangled),
1355 .data = undefined,
1356 });
1357 _ = try c.addToken(.semicolon, ";");
1358
1359 return c.addNode(.{
1360 .tag = .simple_var_decl,
1361 .main_token = mut_tok,
1362 .data = .{
1363 .lhs = 0,
1364 .rhs = init,
1365 },
1366 });
1367 },
1368 .int_cast => {
1369 const payload = node.castTag(.int_cast).?.data;
1370 return renderBuiltinCall(c, "@intCast", &.{payload});
1371 },
1372 .const_cast => {
1373 const payload = node.castTag(.const_cast).?.data;
1374 return renderBuiltinCall(c, "@constCast", &.{payload});
1375 },
1376 .volatile_cast => {
1377 const payload = node.castTag(.volatile_cast).?.data;
1378 return renderBuiltinCall(c, "@volatileCast", &.{payload});
1379 },
1380 .signed_remainder => {
1381 const payload = node.castTag(.signed_remainder).?.data;
1382 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "signedRemainder" });
1383 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
1384 },
1385 .div_trunc => {
1386 const payload = node.castTag(.div_trunc).?.data;
1387 return renderBuiltinCall(c, "@divTrunc", &.{ payload.lhs, payload.rhs });
1388 },
1389 .int_from_bool => {
1390 const payload = node.castTag(.int_from_bool).?.data;
1391 return renderBuiltinCall(c, "@intFromBool", &.{payload});
1392 },
1393 .as => {
1394 const payload = node.castTag(.as).?.data;
1395 return renderBuiltinCall(c, "@as", &.{ payload.lhs, payload.rhs });
1396 },
1397 .truncate => {
1398 const payload = node.castTag(.truncate).?.data;
1399 return renderBuiltinCall(c, "@truncate", &.{payload});
1400 },
1401 .bit_cast => {
1402 const payload = node.castTag(.bit_cast).?.data;
1403 return renderBuiltinCall(c, "@bitCast", &.{payload});
1404 },
1405 .float_cast => {
1406 const payload = node.castTag(.float_cast).?.data;
1407 return renderBuiltinCall(c, "@floatCast", &.{payload});
1408 },
1409 .int_from_float => {
1410 const payload = node.castTag(.int_from_float).?.data;
1411 return renderBuiltinCall(c, "@intFromFloat", &.{payload});
1412 },
1413 .float_from_int => {
1414 const payload = node.castTag(.float_from_int).?.data;
1415 return renderBuiltinCall(c, "@floatFromInt", &.{payload});
1416 },
1417 .ptr_from_int => {
1418 const payload = node.castTag(.ptr_from_int).?.data;
1419 return renderBuiltinCall(c, "@ptrFromInt", &.{payload});
1420 },
1421 .int_from_ptr => {
1422 const payload = node.castTag(.int_from_ptr).?.data;
1423 return renderBuiltinCall(c, "@intFromPtr", &.{payload});
1424 },
1425 .align_cast => {
1426 const payload = node.castTag(.align_cast).?.data;
1427 return renderBuiltinCall(c, "@alignCast", &.{payload});
1428 },
1429 .ptr_cast => {
1430 const payload = node.castTag(.ptr_cast).?.data;
1431 return renderBuiltinCall(c, "@ptrCast", &.{payload});
1432 },
1433 .div_exact => {
1434 const payload = node.castTag(.div_exact).?.data;
1435 return renderBuiltinCall(c, "@divExact", &.{ payload.lhs, payload.rhs });
1436 },
1437 .offset_of => {
1438 const payload = node.castTag(.offset_of).?.data;
1439 return renderBuiltinCall(c, "@offsetOf", &.{ payload.lhs, payload.rhs });
1440 },
1441 .sizeof => {
1442 const payload = node.castTag(.sizeof).?.data;
1443 return renderBuiltinCall(c, "@sizeOf", &.{payload});
1444 },
1445 .shuffle => {
1446 const payload = node.castTag(.shuffle).?.data;
1447 return renderBuiltinCall(c, "@shuffle", &.{
1448 payload.element_type,
1449 payload.a,
1450 payload.b,
1451 payload.mask_vector,
1452 });
1453 },
1454 .builtin_extern => {
1455 const payload = node.castTag(.builtin_extern).?.data;
1456
1457 var info_inits: [1]Payload.ContainerInitDot.Initializer = .{
1458 .{ .name = "name", .value = payload.name },
1459 };
1460 var info_payload: Payload.ContainerInitDot = .{
1461 .base = .{ .tag = .container_init_dot },
1462 .data = &info_inits,
1463 };
1464
1465 return renderBuiltinCall(c, "@extern", &.{
1466 payload.type,
1467 .{ .ptr_otherwise = &info_payload.base },
1468 });
1469 },
1470 .macro_arithmetic => {
1471 const payload = node.castTag(.macro_arithmetic).?.data;
1472 const op = @tagName(payload.op);
1473 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "MacroArithmetic", op });
1474 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
1475 },
1476 .alignof => {
1477 const payload = node.castTag(.alignof).?.data;
1478 return renderBuiltinCall(c, "@alignOf", &.{payload});
1479 },
1480 .typeof => {
1481 const payload = node.castTag(.typeof).?.data;
1482 return renderBuiltinCall(c, "@TypeOf", &.{payload});
1483 },
1484 .typeinfo => {
1485 const payload = node.castTag(.typeinfo).?.data;
1486 return renderBuiltinCall(c, "@typeInfo", &.{payload});
1487 },
1488 .negate => return renderPrefixOp(c, node, .negation, .minus, "-"),
1489 .negate_wrap => return renderPrefixOp(c, node, .negation_wrap, .minus_percent, "-%"),
1490 .bit_not => return renderPrefixOp(c, node, .bit_not, .tilde, "~"),
1491 .not => return renderPrefixOp(c, node, .bool_not, .bang, "!"),
1492 .optional_type => return renderPrefixOp(c, node, .optional_type, .question_mark, "?"),
1493 .address_of => {
1494 const payload = node.castTag(.address_of).?.data;
1495
1496 const ampersand = try c.addToken(.ampersand, "&");
1497 const base = if (payload.tag() == .fn_identifier)
1498 try c.addNode(.{
1499 .tag = .identifier,
1500 .main_token = try c.addIdentifier(payload.castTag(.fn_identifier).?.data),
1501 .data = undefined,
1502 })
1503 else
1504 try renderNodeGrouped(c, payload);
1505 return c.addNode(.{
1506 .tag = .address_of,
1507 .main_token = ampersand,
1508 .data = .{
1509 .lhs = base,
1510 .rhs = undefined,
1511 },
1512 });
1513 },
1514 .deref => {
1515 const payload = node.castTag(.deref).?.data;
1516 const operand = try renderNodeGrouped(c, payload);
1517 const deref_tok = try c.addToken(.period_asterisk, ".*");
1518 return c.addNode(.{
1519 .tag = .deref,
1520 .main_token = deref_tok,
1521 .data = .{
1522 .lhs = operand,
1523 .rhs = undefined,
1524 },
1525 });
1526 },
1527 .unwrap => {
1528 const payload = node.castTag(.unwrap).?.data;
1529 const operand = try renderNodeGrouped(c, payload);
1530 const period = try c.addToken(.period, ".");
1531 const question_mark = try c.addToken(.question_mark, "?");
1532 return c.addNode(.{
1533 .tag = .unwrap_optional,
1534 .main_token = period,
1535 .data = .{
1536 .lhs = operand,
1537 .rhs = question_mark,
1538 },
1539 });
1540 },
1541 .c_pointer, .single_pointer => {
1542 const payload = @as(*Payload.Pointer, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
1543
1544 const main_token = if (node.tag() == .single_pointer)
1545 try c.addToken(.asterisk, "*")
1546 else blk: {
1547 const res = try c.addToken(.l_bracket, "[");
1548 _ = try c.addToken(.asterisk, "*");
1549 _ = try c.addIdentifier("c");
1550 _ = try c.addToken(.r_bracket, "]");
1551 break :blk res;
1552 };
1553 if (payload.is_const) _ = try c.addToken(.keyword_const, "const");
1554 if (payload.is_volatile) _ = try c.addToken(.keyword_volatile, "volatile");
1555 const elem_type = try renderNodeGrouped(c, payload.elem_type);
1556
1557 return c.addNode(.{
1558 .tag = .ptr_type_aligned,
1559 .main_token = main_token,
1560 .data = .{
1561 .lhs = 0,
1562 .rhs = elem_type,
1563 },
1564 });
1565 },
1566 .add => return renderBinOpGrouped(c, node, .add, .plus, "+"),
1567 .add_assign => return renderBinOp(c, node, .assign_add, .plus_equal, "+="),
1568 .add_wrap => return renderBinOpGrouped(c, node, .add_wrap, .plus_percent, "+%"),
1569 .add_wrap_assign => return renderBinOp(c, node, .assign_add_wrap, .plus_percent_equal, "+%="),
1570 .sub => return renderBinOpGrouped(c, node, .sub, .minus, "-"),
1571 .sub_assign => return renderBinOp(c, node, .assign_sub, .minus_equal, "-="),
1572 .sub_wrap => return renderBinOpGrouped(c, node, .sub_wrap, .minus_percent, "-%"),
1573 .sub_wrap_assign => return renderBinOp(c, node, .assign_sub_wrap, .minus_percent_equal, "-%="),
1574 .mul => return renderBinOpGrouped(c, node, .mul, .asterisk, "*"),
1575 .mul_assign => return renderBinOp(c, node, .assign_mul, .asterisk_equal, "*="),
1576 .mul_wrap => return renderBinOpGrouped(c, node, .mul_wrap, .asterisk_percent, "*%"),
1577 .mul_wrap_assign => return renderBinOp(c, node, .assign_mul_wrap, .asterisk_percent_equal, "*%="),
1578 .div => return renderBinOpGrouped(c, node, .div, .slash, "/"),
1579 .div_assign => return renderBinOp(c, node, .assign_div, .slash_equal, "/="),
1580 .shl => return renderBinOpGrouped(c, node, .shl, .angle_bracket_angle_bracket_left, "<<"),
1581 .shl_assign => return renderBinOp(c, node, .assign_shl, .angle_bracket_angle_bracket_left_equal, "<<="),
1582 .shr => return renderBinOpGrouped(c, node, .shr, .angle_bracket_angle_bracket_right, ">>"),
1583 .shr_assign => return renderBinOp(c, node, .assign_shr, .angle_bracket_angle_bracket_right_equal, ">>="),
1584 .mod => return renderBinOpGrouped(c, node, .mod, .percent, "%"),
1585 .mod_assign => return renderBinOp(c, node, .assign_mod, .percent_equal, "%="),
1586 .@"and" => return renderBinOpGrouped(c, node, .bool_and, .keyword_and, "and"),
1587 .@"or" => return renderBinOpGrouped(c, node, .bool_or, .keyword_or, "or"),
1588 .less_than => return renderBinOpGrouped(c, node, .less_than, .angle_bracket_left, "<"),
1589 .less_than_equal => return renderBinOpGrouped(c, node, .less_or_equal, .angle_bracket_left_equal, "<="),
1590 .greater_than => return renderBinOpGrouped(c, node, .greater_than, .angle_bracket_right, ">="),
1591 .greater_than_equal => return renderBinOpGrouped(c, node, .greater_or_equal, .angle_bracket_right_equal, ">="),
1592 .equal => return renderBinOpGrouped(c, node, .equal_equal, .equal_equal, "=="),
1593 .not_equal => return renderBinOpGrouped(c, node, .bang_equal, .bang_equal, "!="),
1594 .bit_and => return renderBinOpGrouped(c, node, .bit_and, .ampersand, "&"),
1595 .bit_and_assign => return renderBinOp(c, node, .assign_bit_and, .ampersand_equal, "&="),
1596 .bit_or => return renderBinOpGrouped(c, node, .bit_or, .pipe, "|"),
1597 .bit_or_assign => return renderBinOp(c, node, .assign_bit_or, .pipe_equal, "|="),
1598 .bit_xor => return renderBinOpGrouped(c, node, .bit_xor, .caret, "^"),
1599 .bit_xor_assign => return renderBinOp(c, node, .assign_bit_xor, .caret_equal, "^="),
1600 .array_cat => return renderBinOp(c, node, .array_cat, .plus_plus, "++"),
1601 .ellipsis3 => return renderBinOpGrouped(c, node, .switch_range, .ellipsis3, "..."),
1602 .assign => return renderBinOp(c, node, .assign, .equal, "="),
1603 .empty_block => {
1604 const l_brace = try c.addToken(.l_brace, "{");
1605 _ = try c.addToken(.r_brace, "}");
1606 return c.addNode(.{
1607 .tag = .block_two,
1608 .main_token = l_brace,
1609 .data = .{
1610 .lhs = 0,
1611 .rhs = 0,
1612 },
1613 });
1614 },
1615 .block_single => {
1616 const payload = node.castTag(.block_single).?.data;
1617 const l_brace = try c.addToken(.l_brace, "{");
1618
1619 const stmt = try renderNode(c, payload);
1620 try addSemicolonIfNeeded(c, payload);
1621
1622 _ = try c.addToken(.r_brace, "}");
1623 return c.addNode(.{
1624 .tag = .block_two_semicolon,
1625 .main_token = l_brace,
1626 .data = .{
1627 .lhs = stmt,
1628 .rhs = 0,
1629 },
1630 });
1631 },
1632 .block => {
1633 const payload = node.castTag(.block).?.data;
1634 if (payload.label) |some| {
1635 _ = try c.addIdentifier(some);
1636 _ = try c.addToken(.colon, ":");
1637 }
1638 const l_brace = try c.addToken(.l_brace, "{");
1639
1640 var stmts = std.ArrayList(NodeIndex).init(c.gpa);
1641 defer stmts.deinit();
1642 for (payload.stmts) |stmt| {
1643 const res = try renderNode(c, stmt);
1644 if (res == 0) continue;
1645 try addSemicolonIfNeeded(c, stmt);
1646 try stmts.append(res);
1647 }
1648 const span = try c.listToSpan(stmts.items);
1649 _ = try c.addToken(.r_brace, "}");
1650
1651 const semicolon = c.tokens.items(.tag)[c.tokens.len - 2] == .semicolon;
1652 return c.addNode(.{
1653 .tag = if (semicolon) .block_semicolon else .block,
1654 .main_token = l_brace,
1655 .data = .{
1656 .lhs = span.start,
1657 .rhs = span.end,
1658 },
1659 });
1660 },
1661 .func => return renderFunc(c, node),
1662 .pub_inline_fn => return renderMacroFunc(c, node),
1663 .discard => {
1664 const payload = node.castTag(.discard).?.data;
1665 if (payload.should_skip) return @as(NodeIndex, 0);
1666
1667 const lhs = try c.addNode(.{
1668 .tag = .identifier,
1669 .main_token = try c.addToken(.identifier, "_"),
1670 .data = undefined,
1671 });
1672 const main_token = try c.addToken(.equal, "=");
1673 if (payload.value.tag() == .identifier) {
1674 // Render as `_ = &foo;` to avoid tripping "pointless discard" and "local variable never mutated" errors.
1675 var addr_of_pl: Payload.UnOp = .{
1676 .base = .{ .tag = .address_of },
1677 .data = payload.value,
1678 };
1679 const addr_of: Node = .{ .ptr_otherwise = &addr_of_pl.base };
1680 return c.addNode(.{
1681 .tag = .assign,
1682 .main_token = main_token,
1683 .data = .{
1684 .lhs = lhs,
1685 .rhs = try renderNode(c, addr_of),
1686 },
1687 });
1688 } else {
1689 return c.addNode(.{
1690 .tag = .assign,
1691 .main_token = main_token,
1692 .data = .{
1693 .lhs = lhs,
1694 .rhs = try renderNode(c, payload.value),
1695 },
1696 });
1697 }
1698 },
1699 .@"while" => {
1700 const payload = node.castTag(.@"while").?.data;
1701 const while_tok = try c.addToken(.keyword_while, "while");
1702 _ = try c.addToken(.l_paren, "(");
1703 const cond = try renderNode(c, payload.cond);
1704 _ = try c.addToken(.r_paren, ")");
1705
1706 const cont_expr = if (payload.cont_expr) |some| blk: {
1707 _ = try c.addToken(.colon, ":");
1708 _ = try c.addToken(.l_paren, "(");
1709 const res = try renderNode(c, some);
1710 _ = try c.addToken(.r_paren, ")");
1711 break :blk res;
1712 } else 0;
1713 const body = try renderNode(c, payload.body);
1714
1715 if (cont_expr == 0) {
1716 return c.addNode(.{
1717 .tag = .while_simple,
1718 .main_token = while_tok,
1719 .data = .{
1720 .lhs = cond,
1721 .rhs = body,
1722 },
1723 });
1724 } else {
1725 return c.addNode(.{
1726 .tag = .while_cont,
1727 .main_token = while_tok,
1728 .data = .{
1729 .lhs = cond,
1730 .rhs = try c.addExtra(std.zig.Ast.Node.WhileCont{
1731 .cont_expr = cont_expr,
1732 .then_expr = body,
1733 }),
1734 },
1735 });
1736 }
1737 },
1738 .while_true => {
1739 const payload = node.castTag(.while_true).?.data;
1740 const while_tok = try c.addToken(.keyword_while, "while");
1741 _ = try c.addToken(.l_paren, "(");
1742 const cond = try c.addNode(.{
1743 .tag = .identifier,
1744 .main_token = try c.addToken(.identifier, "true"),
1745 .data = undefined,
1746 });
1747 _ = try c.addToken(.r_paren, ")");
1748 const body = try renderNode(c, payload);
1749
1750 return c.addNode(.{
1751 .tag = .while_simple,
1752 .main_token = while_tok,
1753 .data = .{
1754 .lhs = cond,
1755 .rhs = body,
1756 },
1757 });
1758 },
1759 .@"if" => {
1760 const payload = node.castTag(.@"if").?.data;
1761 const if_tok = try c.addToken(.keyword_if, "if");
1762 _ = try c.addToken(.l_paren, "(");
1763 const cond = try renderNode(c, payload.cond);
1764 _ = try c.addToken(.r_paren, ")");
1765
1766 const then_expr = try renderNode(c, payload.then);
1767 const else_node = payload.@"else" orelse return c.addNode(.{
1768 .tag = .if_simple,
1769 .main_token = if_tok,
1770 .data = .{
1771 .lhs = cond,
1772 .rhs = then_expr,
1773 },
1774 });
1775 _ = try c.addToken(.keyword_else, "else");
1776 const else_expr = try renderNode(c, else_node);
1777
1778 return c.addNode(.{
1779 .tag = .@"if",
1780 .main_token = if_tok,
1781 .data = .{
1782 .lhs = cond,
1783 .rhs = try c.addExtra(std.zig.Ast.Node.If{
1784 .then_expr = then_expr,
1785 .else_expr = else_expr,
1786 }),
1787 },
1788 });
1789 },
1790 .if_not_break => {
1791 const payload = node.castTag(.if_not_break).?.data;
1792 const if_tok = try c.addToken(.keyword_if, "if");
1793 _ = try c.addToken(.l_paren, "(");
1794 const cond = try c.addNode(.{
1795 .tag = .bool_not,
1796 .main_token = try c.addToken(.bang, "!"),
1797 .data = .{
1798 .lhs = try renderNodeGrouped(c, payload),
1799 .rhs = undefined,
1800 },
1801 });
1802 _ = try c.addToken(.r_paren, ")");
1803 const then_expr = try c.addNode(.{
1804 .tag = .@"break",
1805 .main_token = try c.addToken(.keyword_break, "break"),
1806 .data = .{
1807 .lhs = 0,
1808 .rhs = 0,
1809 },
1810 });
1811
1812 return c.addNode(.{
1813 .tag = .if_simple,
1814 .main_token = if_tok,
1815 .data = .{
1816 .lhs = cond,
1817 .rhs = then_expr,
1818 },
1819 });
1820 },
1821 .@"switch" => {
1822 const payload = node.castTag(.@"switch").?.data;
1823 const switch_tok = try c.addToken(.keyword_switch, "switch");
1824 _ = try c.addToken(.l_paren, "(");
1825 const cond = try renderNode(c, payload.cond);
1826 _ = try c.addToken(.r_paren, ")");
1827
1828 _ = try c.addToken(.l_brace, "{");
1829 var cases = try c.gpa.alloc(NodeIndex, payload.cases.len);
1830 defer c.gpa.free(cases);
1831 for (payload.cases, 0..) |case, i| {
1832 cases[i] = try renderNode(c, case);
1833 _ = try c.addToken(.comma, ",");
1834 }
1835 const span = try c.listToSpan(cases);
1836 _ = try c.addToken(.r_brace, "}");
1837 return c.addNode(.{
1838 .tag = .switch_comma,
1839 .main_token = switch_tok,
1840 .data = .{
1841 .lhs = cond,
1842 .rhs = try c.addExtra(NodeSubRange{
1843 .start = span.start,
1844 .end = span.end,
1845 }),
1846 },
1847 });
1848 },
1849 .switch_else => {
1850 const payload = node.castTag(.switch_else).?.data;
1851 _ = try c.addToken(.keyword_else, "else");
1852 return c.addNode(.{
1853 .tag = .switch_case_one,
1854 .main_token = try c.addToken(.equal_angle_bracket_right, "=>"),
1855 .data = .{
1856 .lhs = 0,
1857 .rhs = try renderNode(c, payload),
1858 },
1859 });
1860 },
1861 .switch_prong => {
1862 const payload = node.castTag(.switch_prong).?.data;
1863 var items = try c.gpa.alloc(NodeIndex, @max(payload.cases.len, 1));
1864 defer c.gpa.free(items);
1865 items[0] = 0;
1866 for (payload.cases, 0..) |item, i| {
1867 if (i != 0) _ = try c.addToken(.comma, ",");
1868 items[i] = try renderNode(c, item);
1869 }
1870 _ = try c.addToken(.r_brace, "}");
1871 if (items.len < 2) {
1872 return c.addNode(.{
1873 .tag = .switch_case_one,
1874 .main_token = try c.addToken(.equal_angle_bracket_right, "=>"),
1875 .data = .{
1876 .lhs = items[0],
1877 .rhs = try renderNode(c, payload.cond),
1878 },
1879 });
1880 } else {
1881 const span = try c.listToSpan(items);
1882 return c.addNode(.{
1883 .tag = .switch_case,
1884 .main_token = try c.addToken(.equal_angle_bracket_right, "=>"),
1885 .data = .{
1886 .lhs = try c.addExtra(NodeSubRange{
1887 .start = span.start,
1888 .end = span.end,
1889 }),
1890 .rhs = try renderNode(c, payload.cond),
1891 },
1892 });
1893 }
1894 },
1895 .opaque_literal => {
1896 const opaque_tok = try c.addToken(.keyword_opaque, "opaque");
1897 _ = try c.addToken(.l_brace, "{");
1898 _ = try c.addToken(.r_brace, "}");
1899
1900 return c.addNode(.{
1901 .tag = .container_decl_two,
1902 .main_token = opaque_tok,
1903 .data = .{
1904 .lhs = 0,
1905 .rhs = 0,
1906 },
1907 });
1908 },
1909 .array_access => {
1910 const payload = node.castTag(.array_access).?.data;
1911 const lhs = try renderNodeGrouped(c, payload.lhs);
1912 const l_bracket = try c.addToken(.l_bracket, "[");
1913 const index_expr = try renderNode(c, payload.rhs);
1914 _ = try c.addToken(.r_bracket, "]");
1915 return c.addNode(.{
1916 .tag = .array_access,
1917 .main_token = l_bracket,
1918 .data = .{
1919 .lhs = lhs,
1920 .rhs = index_expr,
1921 },
1922 });
1923 },
1924 .array_type => {
1925 const payload = node.castTag(.array_type).?.data;
1926 return renderArrayType(c, payload.len, payload.elem_type);
1927 },
1928 .null_sentinel_array_type => {
1929 const payload = node.castTag(.null_sentinel_array_type).?.data;
1930 return renderNullSentinelArrayType(c, payload.len, payload.elem_type);
1931 },
1932 .array_filler => {
1933 const payload = node.castTag(.array_filler).?.data;
1934
1935 const type_expr = try renderArrayType(c, 1, payload.type);
1936 const l_brace = try c.addToken(.l_brace, "{");
1937 const val = try renderNode(c, payload.filler);
1938 _ = try c.addToken(.r_brace, "}");
1939
1940 const init = try c.addNode(.{
1941 .tag = .array_init_one,
1942 .main_token = l_brace,
1943 .data = .{
1944 .lhs = type_expr,
1945 .rhs = val,
1946 },
1947 });
1948 return c.addNode(.{
1949 .tag = .array_cat,
1950 .main_token = try c.addToken(.asterisk_asterisk, "**"),
1951 .data = .{
1952 .lhs = init,
1953 .rhs = try c.addNode(.{
1954 .tag = .number_literal,
1955 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{payload.count}),
1956 .data = undefined,
1957 }),
1958 },
1959 });
1960 },
1961 .empty_array => {
1962 const payload = node.castTag(.empty_array).?.data;
1963
1964 const type_expr = try renderArrayType(c, 0, payload);
1965 return renderArrayInit(c, type_expr, &.{});
1966 },
1967 .array_init => {
1968 const payload = node.castTag(.array_init).?.data;
1969 const type_expr = try renderNode(c, payload.cond);
1970 return renderArrayInit(c, type_expr, payload.cases);
1971 },
1972 .vector_zero_init => {
1973 const payload = node.castTag(.vector_zero_init).?.data;
1974 return renderBuiltinCall(c, "@splat", &.{payload});
1975 },
1976 .field_access => {
1977 const payload = node.castTag(.field_access).?.data;
1978 const lhs = try renderNodeGrouped(c, payload.lhs);
1979 return renderFieldAccess(c, lhs, payload.field_name);
1980 },
1981 .@"struct", .@"union" => return renderRecord(c, node),
1982 .enum_constant => {
1983 const payload = node.castTag(.enum_constant).?.data;
1984
1985 if (payload.is_public) _ = try c.addToken(.keyword_pub, "pub");
1986 const const_tok = try c.addToken(.keyword_const, "const");
1987 _ = try c.addIdentifier(payload.name);
1988
1989 const type_node = if (payload.type) |enum_const_type| blk: {
1990 _ = try c.addToken(.colon, ":");
1991 break :blk try renderNode(c, enum_const_type);
1992 } else 0;
1993
1994 _ = try c.addToken(.equal, "=");
1995
1996 const init_node = try renderNode(c, payload.value);
1997 _ = try c.addToken(.semicolon, ";");
1998
1999 return c.addNode(.{
2000 .tag = .simple_var_decl,
2001 .main_token = const_tok,
2002 .data = .{
2003 .lhs = type_node,
2004 .rhs = init_node,
2005 },
2006 });
2007 },
2008 .tuple => {
2009 const payload = node.castTag(.tuple).?.data;
2010 _ = try c.addToken(.period, ".");
2011 const l_brace = try c.addToken(.l_brace, "{");
2012 var inits = try c.gpa.alloc(NodeIndex, @max(payload.len, 2));
2013 defer c.gpa.free(inits);
2014 inits[0] = 0;
2015 inits[1] = 0;
2016 for (payload, 0..) |init, i| {
2017 if (i != 0) _ = try c.addToken(.comma, ",");
2018 inits[i] = try renderNode(c, init);
2019 }
2020 _ = try c.addToken(.r_brace, "}");
2021 if (payload.len < 3) {
2022 return c.addNode(.{
2023 .tag = .array_init_dot_two,
2024 .main_token = l_brace,
2025 .data = .{
2026 .lhs = inits[0],
2027 .rhs = inits[1],
2028 },
2029 });
2030 } else {
2031 const span = try c.listToSpan(inits);
2032 return c.addNode(.{
2033 .tag = .array_init_dot,
2034 .main_token = l_brace,
2035 .data = .{
2036 .lhs = span.start,
2037 .rhs = span.end,
2038 },
2039 });
2040 }
2041 },
2042 .container_init_dot => {
2043 const payload = node.castTag(.container_init_dot).?.data;
2044 _ = try c.addToken(.period, ".");
2045 const l_brace = try c.addToken(.l_brace, "{");
2046 var inits = try c.gpa.alloc(NodeIndex, @max(payload.len, 2));
2047 defer c.gpa.free(inits);
2048 inits[0] = 0;
2049 inits[1] = 0;
2050 for (payload, 0..) |init, i| {
2051 _ = try c.addToken(.period, ".");
2052 _ = try c.addIdentifier(init.name);
2053 _ = try c.addToken(.equal, "=");
2054 inits[i] = try renderNode(c, init.value);
2055 _ = try c.addToken(.comma, ",");
2056 }
2057 _ = try c.addToken(.r_brace, "}");
2058
2059 if (payload.len < 3) {
2060 return c.addNode(.{
2061 .tag = .struct_init_dot_two_comma,
2062 .main_token = l_brace,
2063 .data = .{
2064 .lhs = inits[0],
2065 .rhs = inits[1],
2066 },
2067 });
2068 } else {
2069 const span = try c.listToSpan(inits);
2070 return c.addNode(.{
2071 .tag = .struct_init_dot_comma,
2072 .main_token = l_brace,
2073 .data = .{
2074 .lhs = span.start,
2075 .rhs = span.end,
2076 },
2077 });
2078 }
2079 },
2080 .container_init => {
2081 const payload = node.castTag(.container_init).?.data;
2082 const lhs = try renderNode(c, payload.lhs);
2083
2084 const l_brace = try c.addToken(.l_brace, "{");
2085 var inits = try c.gpa.alloc(NodeIndex, @max(payload.inits.len, 1));
2086 defer c.gpa.free(inits);
2087 inits[0] = 0;
2088 for (payload.inits, 0..) |init, i| {
2089 _ = try c.addToken(.period, ".");
2090 _ = try c.addIdentifier(init.name);
2091 _ = try c.addToken(.equal, "=");
2092 inits[i] = try renderNode(c, init.value);
2093 _ = try c.addToken(.comma, ",");
2094 }
2095 _ = try c.addToken(.r_brace, "}");
2096
2097 return switch (payload.inits.len) {
2098 0 => c.addNode(.{
2099 .tag = .struct_init_one,
2100 .main_token = l_brace,
2101 .data = .{
2102 .lhs = lhs,
2103 .rhs = 0,
2104 },
2105 }),
2106 1 => c.addNode(.{
2107 .tag = .struct_init_one_comma,
2108 .main_token = l_brace,
2109 .data = .{
2110 .lhs = lhs,
2111 .rhs = inits[0],
2112 },
2113 }),
2114 else => blk: {
2115 const span = try c.listToSpan(inits);
2116 break :blk c.addNode(.{
2117 .tag = .struct_init_comma,
2118 .main_token = l_brace,
2119 .data = .{
2120 .lhs = lhs,
2121 .rhs = try c.addExtra(NodeSubRange{
2122 .start = span.start,
2123 .end = span.end,
2124 }),
2125 },
2126 });
2127 },
2128 };
2129 },
2130 .@"anytype" => unreachable, // Handled in renderParams
2131 }
2132}
2133
2134fn renderRecord(c: *Context, node: Node) !NodeIndex {
2135 const payload = @as(*Payload.Record, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
2136 if (payload.layout == .@"packed")
2137 _ = try c.addToken(.keyword_packed, "packed")
2138 else if (payload.layout == .@"extern")
2139 _ = try c.addToken(.keyword_extern, "extern");
2140 const kind_tok = if (node.tag() == .@"struct")
2141 try c.addToken(.keyword_struct, "struct")
2142 else
2143 try c.addToken(.keyword_union, "union");
2144
2145 _ = try c.addToken(.l_brace, "{");
2146
2147 const num_vars = payload.variables.len;
2148 const num_funcs = payload.functions.len;
2149 const total_members = payload.fields.len + num_vars + num_funcs;
2150 const members = try c.gpa.alloc(NodeIndex, @max(total_members, 2));
2151 defer c.gpa.free(members);
2152 members[0] = 0;
2153 members[1] = 0;
2154
2155 for (payload.fields, 0..) |field, i| {
2156 const name_tok = try c.addTokenFmt(.identifier, "{p}", .{std.zig.fmtId(field.name)});
2157 _ = try c.addToken(.colon, ":");
2158 const type_expr = try renderNode(c, field.type);
2159
2160 const align_expr = if (field.alignment) |alignment| blk: {
2161 _ = try c.addToken(.keyword_align, "align");
2162 _ = try c.addToken(.l_paren, "(");
2163 const align_expr = try c.addNode(.{
2164 .tag = .number_literal,
2165 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{alignment}),
2166 .data = undefined,
2167 });
2168 _ = try c.addToken(.r_paren, ")");
2169 break :blk align_expr;
2170 } else 0;
2171
2172 const value_expr = if (field.default_value) |value| blk: {
2173 _ = try c.addToken(.equal, "=");
2174 break :blk try renderNode(c, value);
2175 } else 0;
2176
2177 members[i] = try c.addNode(if (align_expr == 0) .{
2178 .tag = .container_field_init,
2179 .main_token = name_tok,
2180 .data = .{
2181 .lhs = type_expr,
2182 .rhs = value_expr,
2183 },
2184 } else if (value_expr == 0) .{
2185 .tag = .container_field_align,
2186 .main_token = name_tok,
2187 .data = .{
2188 .lhs = type_expr,
2189 .rhs = align_expr,
2190 },
2191 } else .{
2192 .tag = .container_field,
2193 .main_token = name_tok,
2194 .data = .{
2195 .lhs = type_expr,
2196 .rhs = try c.addExtra(std.zig.Ast.Node.ContainerField{
2197 .align_expr = align_expr,
2198 .value_expr = value_expr,
2199 }),
2200 },
2201 });
2202 _ = try c.addToken(.comma, ",");
2203 }
2204 for (payload.variables, 0..) |variable, i| {
2205 members[payload.fields.len + i] = try renderNode(c, variable);
2206 }
2207 for (payload.functions, 0..) |function, i| {
2208 members[payload.fields.len + num_vars + i] = try renderNode(c, function);
2209 }
2210 _ = try c.addToken(.r_brace, "}");
2211
2212 if (total_members == 0) {
2213 return c.addNode(.{
2214 .tag = .container_decl_two,
2215 .main_token = kind_tok,
2216 .data = .{
2217 .lhs = 0,
2218 .rhs = 0,
2219 },
2220 });
2221 } else if (total_members <= 2) {
2222 return c.addNode(.{
2223 .tag = if (num_funcs == 0) .container_decl_two_trailing else .container_decl_two,
2224 .main_token = kind_tok,
2225 .data = .{
2226 .lhs = members[0],
2227 .rhs = members[1],
2228 },
2229 });
2230 } else {
2231 const span = try c.listToSpan(members);
2232 return c.addNode(.{
2233 .tag = if (num_funcs == 0) .container_decl_trailing else .container_decl,
2234 .main_token = kind_tok,
2235 .data = .{
2236 .lhs = span.start,
2237 .rhs = span.end,
2238 },
2239 });
2240 }
2241}
2242
2243fn renderFieldAccess(c: *Context, lhs: NodeIndex, field_name: []const u8) !NodeIndex {
2244 return c.addNode(.{
2245 .tag = .field_access,
2246 .main_token = try c.addToken(.period, "."),
2247 .data = .{
2248 .lhs = lhs,
2249 .rhs = try c.addTokenFmt(.identifier, "{p}", .{std.zig.fmtId(field_name)}),
2250 },
2251 });
2252}
2253
2254fn renderArrayInit(c: *Context, lhs: NodeIndex, inits: []const Node) !NodeIndex {
2255 const l_brace = try c.addToken(.l_brace, "{");
2256 var rendered = try c.gpa.alloc(NodeIndex, @max(inits.len, 1));
2257 defer c.gpa.free(rendered);
2258 rendered[0] = 0;
2259 for (inits, 0..) |init, i| {
2260 rendered[i] = try renderNode(c, init);
2261 _ = try c.addToken(.comma, ",");
2262 }
2263 _ = try c.addToken(.r_brace, "}");
2264 if (inits.len < 2) {
2265 return c.addNode(.{
2266 .tag = .array_init_one_comma,
2267 .main_token = l_brace,
2268 .data = .{
2269 .lhs = lhs,
2270 .rhs = rendered[0],
2271 },
2272 });
2273 } else {
2274 const span = try c.listToSpan(rendered);
2275 return c.addNode(.{
2276 .tag = .array_init_comma,
2277 .main_token = l_brace,
2278 .data = .{
2279 .lhs = lhs,
2280 .rhs = try c.addExtra(NodeSubRange{
2281 .start = span.start,
2282 .end = span.end,
2283 }),
2284 },
2285 });
2286 }
2287}
2288
2289fn renderArrayType(c: *Context, len: usize, elem_type: Node) !NodeIndex {
2290 const l_bracket = try c.addToken(.l_bracket, "[");
2291 const len_expr = try c.addNode(.{
2292 .tag = .number_literal,
2293 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{len}),
2294 .data = undefined,
2295 });
2296 _ = try c.addToken(.r_bracket, "]");
2297 const elem_type_expr = try renderNode(c, elem_type);
2298 return c.addNode(.{
2299 .tag = .array_type,
2300 .main_token = l_bracket,
2301 .data = .{
2302 .lhs = len_expr,
2303 .rhs = elem_type_expr,
2304 },
2305 });
2306}
2307
2308fn renderNullSentinelArrayType(c: *Context, len: usize, elem_type: Node) !NodeIndex {
2309 const l_bracket = try c.addToken(.l_bracket, "[");
2310 const len_expr = try c.addNode(.{
2311 .tag = .number_literal,
2312 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{len}),
2313 .data = undefined,
2314 });
2315 _ = try c.addToken(.colon, ":");
2316
2317 const sentinel_expr = try c.addNode(.{
2318 .tag = .number_literal,
2319 .main_token = try c.addToken(.number_literal, "0"),
2320 .data = undefined,
2321 });
2322
2323 _ = try c.addToken(.r_bracket, "]");
2324 const elem_type_expr = try renderNode(c, elem_type);
2325 return c.addNode(.{
2326 .tag = .array_type_sentinel,
2327 .main_token = l_bracket,
2328 .data = .{
2329 .lhs = len_expr,
2330 .rhs = try c.addExtra(std.zig.Ast.Node.ArrayTypeSentinel{
2331 .sentinel = sentinel_expr,
2332 .elem_type = elem_type_expr,
2333 }),
2334 },
2335 });
2336}
2337
2338fn addSemicolonIfNeeded(c: *Context, node: Node) !void {
2339 switch (node.tag()) {
2340 .warning => unreachable,
2341 .var_decl, .var_simple, .arg_redecl, .alias, .block, .empty_block, .block_single, .@"switch", .static_local_var, .extern_local_var, .mut_str => {},
2342 .while_true => {
2343 const payload = node.castTag(.while_true).?.data;
2344 return addSemicolonIfNotBlock(c, payload);
2345 },
2346 .@"while" => {
2347 const payload = node.castTag(.@"while").?.data;
2348 return addSemicolonIfNotBlock(c, payload.body);
2349 },
2350 .@"if" => {
2351 const payload = node.castTag(.@"if").?.data;
2352 if (payload.@"else") |some|
2353 return addSemicolonIfNeeded(c, some);
2354 return addSemicolonIfNotBlock(c, payload.then);
2355 },
2356 else => _ = try c.addToken(.semicolon, ";"),
2357 }
2358}
2359
2360fn addSemicolonIfNotBlock(c: *Context, node: Node) !void {
2361 switch (node.tag()) {
2362 .block, .empty_block, .block_single => {},
2363 else => _ = try c.addToken(.semicolon, ";"),
2364 }
2365}
2366
2367fn renderNodeGrouped(c: *Context, node: Node) !NodeIndex {
2368 switch (node.tag()) {
2369 .declaration => unreachable,
2370 .null_literal,
2371 .undefined_literal,
2372 .true_literal,
2373 .false_literal,
2374 .return_void,
2375 .zero_literal,
2376 .one_literal,
2377 .void_type,
2378 .noreturn_type,
2379 .@"anytype",
2380 .div_trunc,
2381 .signed_remainder,
2382 .int_cast,
2383 .const_cast,
2384 .volatile_cast,
2385 .as,
2386 .truncate,
2387 .bit_cast,
2388 .float_cast,
2389 .int_from_float,
2390 .float_from_int,
2391 .ptr_from_int,
2392 .std_mem_zeroes,
2393 .int_from_ptr,
2394 .sizeof,
2395 .alignof,
2396 .typeof,
2397 .typeinfo,
2398 .vector,
2399 .helpers_sizeof,
2400 .helpers_cast,
2401 .helpers_promoteIntLiteral,
2402 .helpers_shuffle_vector_index,
2403 .helpers_flexible_array_type,
2404 .std_mem_zeroinit,
2405 .integer_literal,
2406 .float_literal,
2407 .string_literal,
2408 .string_slice,
2409 .char_literal,
2410 .enum_literal,
2411 .identifier,
2412 .fn_identifier,
2413 .field_access,
2414 .ptr_cast,
2415 .type,
2416 .array_access,
2417 .align_cast,
2418 .optional_type,
2419 .c_pointer,
2420 .single_pointer,
2421 .unwrap,
2422 .deref,
2423 .not,
2424 .negate,
2425 .negate_wrap,
2426 .bit_not,
2427 .func,
2428 .call,
2429 .array_type,
2430 .null_sentinel_array_type,
2431 .int_from_bool,
2432 .div_exact,
2433 .offset_of,
2434 .shuffle,
2435 .builtin_extern,
2436 .static_local_var,
2437 .extern_local_var,
2438 .mut_str,
2439 .macro_arithmetic,
2440 => {
2441 // no grouping needed
2442 return renderNode(c, node);
2443 },
2444
2445 .opaque_literal,
2446 .empty_array,
2447 .block_single,
2448 .add,
2449 .add_wrap,
2450 .sub,
2451 .sub_wrap,
2452 .mul,
2453 .mul_wrap,
2454 .div,
2455 .shl,
2456 .shr,
2457 .mod,
2458 .@"and",
2459 .@"or",
2460 .less_than,
2461 .less_than_equal,
2462 .greater_than,
2463 .greater_than_equal,
2464 .equal,
2465 .not_equal,
2466 .bit_and,
2467 .bit_or,
2468 .bit_xor,
2469 .empty_block,
2470 .array_cat,
2471 .array_filler,
2472 .@"if",
2473 .@"struct",
2474 .@"union",
2475 .array_init,
2476 .vector_zero_init,
2477 .tuple,
2478 .container_init,
2479 .container_init_dot,
2480 .block,
2481 .address_of,
2482 => return c.addNode(.{
2483 .tag = .grouped_expression,
2484 .main_token = try c.addToken(.l_paren, "("),
2485 .data = .{
2486 .lhs = try renderNode(c, node),
2487 .rhs = try c.addToken(.r_paren, ")"),
2488 },
2489 }),
2490 .ellipsis3,
2491 .switch_prong,
2492 .warning,
2493 .var_decl,
2494 .fail_decl,
2495 .arg_redecl,
2496 .alias,
2497 .var_simple,
2498 .pub_var_simple,
2499 .enum_constant,
2500 .@"while",
2501 .@"switch",
2502 .@"break",
2503 .break_val,
2504 .pub_inline_fn,
2505 .discard,
2506 .@"continue",
2507 .@"return",
2508 .@"comptime",
2509 .@"defer",
2510 .asm_simple,
2511 .while_true,
2512 .if_not_break,
2513 .switch_else,
2514 .add_assign,
2515 .add_wrap_assign,
2516 .sub_assign,
2517 .sub_wrap_assign,
2518 .mul_assign,
2519 .mul_wrap_assign,
2520 .div_assign,
2521 .shl_assign,
2522 .shr_assign,
2523 .mod_assign,
2524 .bit_and_assign,
2525 .bit_or_assign,
2526 .bit_xor_assign,
2527 .assign,
2528 .helpers_macro,
2529 .import_c_builtin,
2530 => {
2531 // these should never appear in places where grouping might be needed.
2532 unreachable;
2533 },
2534 }
2535}
2536
2537fn renderPrefixOp(c: *Context, node: Node, tag: std.zig.Ast.Node.Tag, tok_tag: TokenTag, bytes: []const u8) !NodeIndex {
2538 const payload = @as(*Payload.UnOp, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
2539 return c.addNode(.{
2540 .tag = tag,
2541 .main_token = try c.addToken(tok_tag, bytes),
2542 .data = .{
2543 .lhs = try renderNodeGrouped(c, payload),
2544 .rhs = undefined,
2545 },
2546 });
2547}
2548
2549fn renderBinOpGrouped(c: *Context, node: Node, tag: std.zig.Ast.Node.Tag, tok_tag: TokenTag, bytes: []const u8) !NodeIndex {
2550 const payload = @as(*Payload.BinOp, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
2551 const lhs = try renderNodeGrouped(c, payload.lhs);
2552 return c.addNode(.{
2553 .tag = tag,
2554 .main_token = try c.addToken(tok_tag, bytes),
2555 .data = .{
2556 .lhs = lhs,
2557 .rhs = try renderNodeGrouped(c, payload.rhs),
2558 },
2559 });
2560}
2561
2562fn renderBinOp(c: *Context, node: Node, tag: std.zig.Ast.Node.Tag, tok_tag: TokenTag, bytes: []const u8) !NodeIndex {
2563 const payload = @as(*Payload.BinOp, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
2564 const lhs = try renderNode(c, payload.lhs);
2565 return c.addNode(.{
2566 .tag = tag,
2567 .main_token = try c.addToken(tok_tag, bytes),
2568 .data = .{
2569 .lhs = lhs,
2570 .rhs = try renderNode(c, payload.rhs),
2571 },
2572 });
2573}
2574
2575fn renderStdImport(c: *Context, parts: []const []const u8) !NodeIndex {
2576 const import_tok = try c.addToken(.builtin, "@import");
2577 _ = try c.addToken(.l_paren, "(");
2578 const std_tok = try c.addToken(.string_literal, "\"std\"");
2579 const std_node = try c.addNode(.{
2580 .tag = .string_literal,
2581 .main_token = std_tok,
2582 .data = undefined,
2583 });
2584 _ = try c.addToken(.r_paren, ")");
2585
2586 const import_node = try c.addNode(.{
2587 .tag = .builtin_call_two,
2588 .main_token = import_tok,
2589 .data = .{
2590 .lhs = std_node,
2591 .rhs = 0,
2592 },
2593 });
2594
2595 var access_chain = import_node;
2596 for (parts) |part| {
2597 access_chain = try renderFieldAccess(c, access_chain, part);
2598 }
2599 return access_chain;
2600}
2601
2602fn renderCall(c: *Context, lhs: NodeIndex, args: []const Node) !NodeIndex {
2603 const lparen = try c.addToken(.l_paren, "(");
2604 const res = switch (args.len) {
2605 0 => try c.addNode(.{
2606 .tag = .call_one,
2607 .main_token = lparen,
2608 .data = .{
2609 .lhs = lhs,
2610 .rhs = 0,
2611 },
2612 }),
2613 1 => blk: {
2614 const arg = try renderNode(c, args[0]);
2615 break :blk try c.addNode(.{
2616 .tag = .call_one,
2617 .main_token = lparen,
2618 .data = .{
2619 .lhs = lhs,
2620 .rhs = arg,
2621 },
2622 });
2623 },
2624 else => blk: {
2625 var rendered = try c.gpa.alloc(NodeIndex, args.len);
2626 defer c.gpa.free(rendered);
2627
2628 for (args, 0..) |arg, i| {
2629 if (i != 0) _ = try c.addToken(.comma, ",");
2630 rendered[i] = try renderNode(c, arg);
2631 }
2632 const span = try c.listToSpan(rendered);
2633 break :blk try c.addNode(.{
2634 .tag = .call,
2635 .main_token = lparen,
2636 .data = .{
2637 .lhs = lhs,
2638 .rhs = try c.addExtra(NodeSubRange{
2639 .start = span.start,
2640 .end = span.end,
2641 }),
2642 },
2643 });
2644 },
2645 };
2646 _ = try c.addToken(.r_paren, ")");
2647 return res;
2648}
2649
2650fn renderBuiltinCall(c: *Context, builtin: []const u8, args: []const Node) !NodeIndex {
2651 const builtin_tok = try c.addToken(.builtin, builtin);
2652 _ = try c.addToken(.l_paren, "(");
2653 var arg_1: NodeIndex = 0;
2654 var arg_2: NodeIndex = 0;
2655 var arg_3: NodeIndex = 0;
2656 var arg_4: NodeIndex = 0;
2657 switch (args.len) {
2658 0 => {},
2659 1 => {
2660 arg_1 = try renderNode(c, args[0]);
2661 },
2662 2 => {
2663 arg_1 = try renderNode(c, args[0]);
2664 _ = try c.addToken(.comma, ",");
2665 arg_2 = try renderNode(c, args[1]);
2666 },
2667 4 => {
2668 arg_1 = try renderNode(c, args[0]);
2669 _ = try c.addToken(.comma, ",");
2670 arg_2 = try renderNode(c, args[1]);
2671 _ = try c.addToken(.comma, ",");
2672 arg_3 = try renderNode(c, args[2]);
2673 _ = try c.addToken(.comma, ",");
2674 arg_4 = try renderNode(c, args[3]);
2675 },
2676 else => unreachable, // expand this function as needed.
2677 }
2678
2679 _ = try c.addToken(.r_paren, ")");
2680 if (args.len <= 2) {
2681 return c.addNode(.{
2682 .tag = .builtin_call_two,
2683 .main_token = builtin_tok,
2684 .data = .{
2685 .lhs = arg_1,
2686 .rhs = arg_2,
2687 },
2688 });
2689 } else {
2690 std.debug.assert(args.len == 4);
2691
2692 const params = try c.listToSpan(&.{ arg_1, arg_2, arg_3, arg_4 });
2693 return c.addNode(.{
2694 .tag = .builtin_call,
2695 .main_token = builtin_tok,
2696 .data = .{
2697 .lhs = params.start,
2698 .rhs = params.end,
2699 },
2700 });
2701 }
2702}
2703
2704fn renderVar(c: *Context, node: Node) !NodeIndex {
2705 const payload = node.castTag(.var_decl).?.data;
2706 if (payload.is_pub) _ = try c.addToken(.keyword_pub, "pub");
2707 if (payload.is_extern) _ = try c.addToken(.keyword_extern, "extern");
2708 if (payload.is_export) _ = try c.addToken(.keyword_export, "export");
2709 if (payload.is_threadlocal) _ = try c.addToken(.keyword_threadlocal, "threadlocal");
2710 const mut_tok = if (payload.is_const)
2711 try c.addToken(.keyword_const, "const")
2712 else
2713 try c.addToken(.keyword_var, "var");
2714 _ = try c.addIdentifier(payload.name);
2715 _ = try c.addToken(.colon, ":");
2716 const type_node = try renderNode(c, payload.type);
2717
2718 const align_node = if (payload.alignment) |some| blk: {
2719 _ = try c.addToken(.keyword_align, "align");
2720 _ = try c.addToken(.l_paren, "(");
2721 const res = try c.addNode(.{
2722 .tag = .number_literal,
2723 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{some}),
2724 .data = undefined,
2725 });
2726 _ = try c.addToken(.r_paren, ")");
2727 break :blk res;
2728 } else 0;
2729
2730 const section_node = if (payload.linksection_string) |some| blk: {
2731 _ = try c.addToken(.keyword_linksection, "linksection");
2732 _ = try c.addToken(.l_paren, "(");
2733 const res = try c.addNode(.{
2734 .tag = .string_literal,
2735 .main_token = try c.addTokenFmt(.string_literal, "\"{}\"", .{std.zig.fmtEscapes(some)}),
2736 .data = undefined,
2737 });
2738 _ = try c.addToken(.r_paren, ")");
2739 break :blk res;
2740 } else 0;
2741
2742 const init_node = if (payload.init) |some| blk: {
2743 _ = try c.addToken(.equal, "=");
2744 break :blk try renderNode(c, some);
2745 } else 0;
2746 _ = try c.addToken(.semicolon, ";");
2747
2748 if (section_node == 0) {
2749 if (align_node == 0) {
2750 return c.addNode(.{
2751 .tag = .simple_var_decl,
2752 .main_token = mut_tok,
2753 .data = .{
2754 .lhs = type_node,
2755 .rhs = init_node,
2756 },
2757 });
2758 } else {
2759 return c.addNode(.{
2760 .tag = .local_var_decl,
2761 .main_token = mut_tok,
2762 .data = .{
2763 .lhs = try c.addExtra(std.zig.Ast.Node.LocalVarDecl{
2764 .type_node = type_node,
2765 .align_node = align_node,
2766 }),
2767 .rhs = init_node,
2768 },
2769 });
2770 }
2771 } else {
2772 return c.addNode(.{
2773 .tag = .global_var_decl,
2774 .main_token = mut_tok,
2775 .data = .{
2776 .lhs = try c.addExtra(std.zig.Ast.Node.GlobalVarDecl{
2777 .type_node = type_node,
2778 .align_node = align_node,
2779 .section_node = section_node,
2780 .addrspace_node = 0,
2781 }),
2782 .rhs = init_node,
2783 },
2784 });
2785 }
2786}
2787
2788fn renderFunc(c: *Context, node: Node) !NodeIndex {
2789 const payload = node.castTag(.func).?.data;
2790 if (payload.is_pub) _ = try c.addToken(.keyword_pub, "pub");
2791 if (payload.is_extern) _ = try c.addToken(.keyword_extern, "extern");
2792 if (payload.is_export) _ = try c.addToken(.keyword_export, "export");
2793 if (payload.is_inline) _ = try c.addToken(.keyword_inline, "inline");
2794 const fn_token = try c.addToken(.keyword_fn, "fn");
2795 if (payload.name) |some| _ = try c.addIdentifier(some);
2796
2797 const params = try renderParams(c, payload.params, payload.is_var_args);
2798 defer params.deinit();
2799 var span: NodeSubRange = undefined;
2800 if (params.items.len > 1) span = try c.listToSpan(params.items);
2801
2802 const align_expr = if (payload.alignment) |some| blk: {
2803 _ = try c.addToken(.keyword_align, "align");
2804 _ = try c.addToken(.l_paren, "(");
2805 const res = try c.addNode(.{
2806 .tag = .number_literal,
2807 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{some}),
2808 .data = undefined,
2809 });
2810 _ = try c.addToken(.r_paren, ")");
2811 break :blk res;
2812 } else 0;
2813
2814 const section_expr = if (payload.linksection_string) |some| blk: {
2815 _ = try c.addToken(.keyword_linksection, "linksection");
2816 _ = try c.addToken(.l_paren, "(");
2817 const res = try c.addNode(.{
2818 .tag = .string_literal,
2819 .main_token = try c.addTokenFmt(.string_literal, "\"{}\"", .{std.zig.fmtEscapes(some)}),
2820 .data = undefined,
2821 });
2822 _ = try c.addToken(.r_paren, ")");
2823 break :blk res;
2824 } else 0;
2825
2826 const callconv_expr = if (payload.explicit_callconv) |some| blk: {
2827 _ = try c.addToken(.keyword_callconv, "callconv");
2828 _ = try c.addToken(.l_paren, "(");
2829 const cc_node = switch (some) {
2830 .c => cc_node: {
2831 _ = try c.addToken(.period, ".");
2832 break :cc_node try c.addNode(.{
2833 .tag = .enum_literal,
2834 .main_token = try c.addToken(.identifier, "c"),
2835 .data = undefined,
2836 });
2837 },
2838 .x86_64_sysv,
2839 .x86_64_win,
2840 .x86_stdcall,
2841 .x86_fastcall,
2842 .x86_thiscall,
2843 .x86_vectorcall,
2844 .aarch64_vfabi,
2845 .arm_aapcs,
2846 .arm_aapcs_vfp,
2847 .m68k_rtd,
2848 => cc_node: {
2849 // .{ .foo = .{} }
2850 _ = try c.addToken(.period, ".");
2851 const outer_lbrace = try c.addToken(.l_brace, "{");
2852 _ = try c.addToken(.period, ".");
2853 _ = try c.addToken(.identifier, @tagName(some));
2854 _ = try c.addToken(.equal, "=");
2855 _ = try c.addToken(.period, ".");
2856 const inner_lbrace = try c.addToken(.l_brace, "{");
2857 _ = try c.addToken(.r_brace, "}");
2858 _ = try c.addToken(.r_brace, "}");
2859 break :cc_node try c.addNode(.{
2860 .tag = .struct_init_dot_two,
2861 .main_token = outer_lbrace,
2862 .data = .{
2863 .lhs = try c.addNode(.{
2864 .tag = .struct_init_dot_two,
2865 .main_token = inner_lbrace,
2866 .data = .{ .lhs = 0, .rhs = 0 },
2867 }),
2868 .rhs = 0,
2869 },
2870 });
2871 },
2872 };
2873 _ = try c.addToken(.r_paren, ")");
2874 break :blk cc_node;
2875 } else 0;
2876
2877 const return_type_expr = try renderNode(c, payload.return_type);
2878
2879 const fn_proto = try blk: {
2880 if (align_expr == 0 and section_expr == 0 and callconv_expr == 0) {
2881 if (params.items.len < 2)
2882 break :blk c.addNode(.{
2883 .tag = .fn_proto_simple,
2884 .main_token = fn_token,
2885 .data = .{
2886 .lhs = params.items[0],
2887 .rhs = return_type_expr,
2888 },
2889 })
2890 else
2891 break :blk c.addNode(.{
2892 .tag = .fn_proto_multi,
2893 .main_token = fn_token,
2894 .data = .{
2895 .lhs = try c.addExtra(NodeSubRange{
2896 .start = span.start,
2897 .end = span.end,
2898 }),
2899 .rhs = return_type_expr,
2900 },
2901 });
2902 }
2903 if (params.items.len < 2)
2904 break :blk c.addNode(.{
2905 .tag = .fn_proto_one,
2906 .main_token = fn_token,
2907 .data = .{
2908 .lhs = try c.addExtra(std.zig.Ast.Node.FnProtoOne{
2909 .param = params.items[0],
2910 .align_expr = align_expr,
2911 .addrspace_expr = 0, // TODO
2912 .section_expr = section_expr,
2913 .callconv_expr = callconv_expr,
2914 }),
2915 .rhs = return_type_expr,
2916 },
2917 })
2918 else
2919 break :blk c.addNode(.{
2920 .tag = .fn_proto,
2921 .main_token = fn_token,
2922 .data = .{
2923 .lhs = try c.addExtra(std.zig.Ast.Node.FnProto{
2924 .params_start = span.start,
2925 .params_end = span.end,
2926 .align_expr = align_expr,
2927 .addrspace_expr = 0, // TODO
2928 .section_expr = section_expr,
2929 .callconv_expr = callconv_expr,
2930 }),
2931 .rhs = return_type_expr,
2932 },
2933 });
2934 };
2935
2936 const payload_body = payload.body orelse {
2937 if (payload.is_extern) {
2938 _ = try c.addToken(.semicolon, ";");
2939 }
2940 return fn_proto;
2941 };
2942 const body = try renderNode(c, payload_body);
2943 return c.addNode(.{
2944 .tag = .fn_decl,
2945 .main_token = fn_token,
2946 .data = .{
2947 .lhs = fn_proto,
2948 .rhs = body,
2949 },
2950 });
2951}
2952
2953fn renderMacroFunc(c: *Context, node: Node) !NodeIndex {
2954 const payload = node.castTag(.pub_inline_fn).?.data;
2955 _ = try c.addToken(.keyword_pub, "pub");
2956 _ = try c.addToken(.keyword_inline, "inline");
2957 const fn_token = try c.addToken(.keyword_fn, "fn");
2958 _ = try c.addIdentifier(payload.name);
2959
2960 const params = try renderParams(c, payload.params, false);
2961 defer params.deinit();
2962 var span: NodeSubRange = undefined;
2963 if (params.items.len > 1) span = try c.listToSpan(params.items);
2964
2965 const return_type_expr = try renderNodeGrouped(c, payload.return_type);
2966
2967 const fn_proto = blk: {
2968 if (params.items.len < 2) {
2969 break :blk try c.addNode(.{
2970 .tag = .fn_proto_simple,
2971 .main_token = fn_token,
2972 .data = .{
2973 .lhs = params.items[0],
2974 .rhs = return_type_expr,
2975 },
2976 });
2977 } else {
2978 break :blk try c.addNode(.{
2979 .tag = .fn_proto_multi,
2980 .main_token = fn_token,
2981 .data = .{
2982 .lhs = try c.addExtra(std.zig.Ast.Node.SubRange{
2983 .start = span.start,
2984 .end = span.end,
2985 }),
2986 .rhs = return_type_expr,
2987 },
2988 });
2989 }
2990 };
2991 return c.addNode(.{
2992 .tag = .fn_decl,
2993 .main_token = fn_token,
2994 .data = .{
2995 .lhs = fn_proto,
2996 .rhs = try renderNode(c, payload.body),
2997 },
2998 });
2999}
3000
3001fn renderParams(c: *Context, params: []Payload.Param, is_var_args: bool) !std.ArrayList(NodeIndex) {
3002 _ = try c.addToken(.l_paren, "(");
3003 var rendered = try std.ArrayList(NodeIndex).initCapacity(c.gpa, @max(params.len, 1));
3004 errdefer rendered.deinit();
3005
3006 for (params, 0..) |param, i| {
3007 if (i != 0) _ = try c.addToken(.comma, ",");
3008 if (param.is_noalias) _ = try c.addToken(.keyword_noalias, "noalias");
3009 if (param.name) |some| {
3010 _ = try c.addIdentifier(some);
3011 _ = try c.addToken(.colon, ":");
3012 }
3013 if (param.type.tag() == .@"anytype") {
3014 _ = try c.addToken(.keyword_anytype, "anytype");
3015 continue;
3016 }
3017 rendered.appendAssumeCapacity(try renderNode(c, param.type));
3018 }
3019 if (is_var_args) {
3020 if (params.len != 0) _ = try c.addToken(.comma, ",");
3021 _ = try c.addToken(.ellipsis3, "...");
3022 }
3023 _ = try c.addToken(.r_paren, ")");
3024
3025 if (rendered.items.len == 0) rendered.appendAssumeCapacity(0);
3026 return rendered;
3027}
lib/std/zig.zig+1
...@@ -24,6 +24,7 @@ pub const LibCInstallation = @import("zig/LibCInstallation.zig");...@@ -24,6 +24,7 @@ pub const LibCInstallation = @import("zig/LibCInstallation.zig");
24pub const WindowsSdk = @import("zig/WindowsSdk.zig");24pub const WindowsSdk = @import("zig/WindowsSdk.zig");
25pub const LibCDirs = @import("zig/LibCDirs.zig");25pub const LibCDirs = @import("zig/LibCDirs.zig");
26pub const target = @import("zig/target.zig");26pub const target = @import("zig/target.zig");
27pub const Preprocessor = @import("zig/Preprocessor.zig");
2728
28// Character literal parsing29// Character literal parsing
29pub const ParsedCharLiteral = string_literal.ParsedCharLiteral;30pub const ParsedCharLiteral = string_literal.ParsedCharLiteral;
lib/std/zig/Preprocessor.zig created+3649
...@@ -0,0 +1,3649 @@
1const std = @import("std");
2const mem = std.mem;
3const Allocator = mem.Allocator;
4const assert = std.debug.assert;
5const Compilation = @import("Compilation.zig");
6const Error = Compilation.Error;
7const Source = @import("Source.zig");
8const Tokenizer = @import("Tokenizer.zig");
9const RawToken = Tokenizer.Token;
10const Parser = @import("Parser.zig");
11const Diagnostics = @import("Diagnostics.zig");
12const Tree = @import("Tree.zig");
13const Token = Tree.Token;
14const TokenWithExpansionLocs = Tree.TokenWithExpansionLocs;
15const Attribute = @import("Attribute.zig");
16const features = @import("features.zig");
17const Hideset = @import("Hideset.zig");
18
19const DefineMap = std.StringHashMapUnmanaged(Macro);
20const RawTokenList = std.ArrayList(RawToken);
21const max_include_depth = 200;
22
23/// Errors that can be returned when expanding a macro.
24/// error.UnknownPragma can occur within Preprocessor.pragma() but
25/// it is handled there and doesn't escape that function
26const MacroError = Error || error{StopPreprocessing};
27
28const Macro = struct {
29 /// Parameters of the function type macro
30 params: []const []const u8,
31
32 /// Token constituting the macro body
33 tokens: []const RawToken,
34
35 /// If the function type macro has variable number of arguments
36 var_args: bool,
37
38 /// Is a function type macro
39 is_func: bool,
40
41 /// Is a predefined macro
42 is_builtin: bool = false,
43
44 /// Location of macro in the source
45 loc: Source.Location,
46
47 fn eql(a: Macro, b: Macro, pp: *Preprocessor) bool {
48 if (a.tokens.len != b.tokens.len) return false;
49 if (a.is_builtin != b.is_builtin) return false;
50 for (a.tokens, b.tokens) |a_tok, b_tok| if (!tokEql(pp, a_tok, b_tok)) return false;
51
52 if (a.is_func and b.is_func) {
53 if (a.var_args != b.var_args) return false;
54 if (a.params.len != b.params.len) return false;
55 for (a.params, b.params) |a_param, b_param| if (!mem.eql(u8, a_param, b_param)) return false;
56 }
57
58 return true;
59 }
60
61 fn tokEql(pp: *Preprocessor, a: RawToken, b: RawToken) bool {
62 return mem.eql(u8, pp.tokSlice(a), pp.tokSlice(b));
63 }
64};
65
66const Preprocessor = @This();
67
68const ExpansionEntry = struct {
69 idx: Tree.TokenIndex,
70 locs: [*]Source.Location,
71};
72
73const TokenState = struct {
74 tokens_len: usize,
75 expansion_entries_len: usize,
76};
77
78comp: *Compilation,
79gpa: mem.Allocator,
80arena: std.heap.ArenaAllocator,
81defines: DefineMap = .{},
82/// Do not directly mutate this; use addToken / addTokenAssumeCapacity / ensureTotalTokenCapacity / ensureUnusedTokenCapacity
83tokens: Token.List = .{},
84/// Do not directly mutate this; must be kept in sync with `tokens`
85expansion_entries: std.MultiArrayList(ExpansionEntry) = .{},
86token_buf: RawTokenList,
87char_buf: std.ArrayList(u8),
88/// Counter that is incremented each time preprocess() is called
89/// Can be used to distinguish multiple preprocessings of the same file
90preprocess_count: u32 = 0,
91generated_line: u32 = 1,
92add_expansion_nl: u32 = 0,
93include_depth: u8 = 0,
94counter: u32 = 0,
95expansion_source_loc: Source.Location = undefined,
96poisoned_identifiers: std.StringHashMap(void),
97/// Map from Source.Id to macro name in the `#ifndef` condition which guards the source, if any
98include_guards: std.AutoHashMapUnmanaged(Source.Id, []const u8) = .empty,
99
100/// Store `keyword_define` and `keyword_undef` tokens.
101/// Used to implement preprocessor debug dump options
102/// Must be false unless in -E mode (parser does not handle those token types)
103store_macro_tokens: bool = false,
104
105/// Memory is retained to avoid allocation on every single token.
106top_expansion_buf: ExpandBuf,
107
108/// Dump current state to stderr.
109verbose: bool = false,
110preserve_whitespace: bool = false,
111
112/// linemarker tokens. Must be .none unless in -E mode (parser does not handle linemarkers)
113linemarkers: Linemarkers = .none,
114
115hideset: Hideset,
116
117pub const parse = Parser.parse;
118
119pub const Linemarkers = enum {
120 /// No linemarker tokens. Required setting if parser will run
121 none,
122 /// #line <num> "filename"
123 line_directives,
124 /// # <num> "filename" flags
125 numeric_directives,
126};
127
128pub fn init(comp: *Compilation) Preprocessor {
129 const pp = Preprocessor{
130 .comp = comp,
131 .gpa = comp.gpa,
132 .arena = std.heap.ArenaAllocator.init(comp.gpa),
133 .token_buf = RawTokenList.init(comp.gpa),
134 .char_buf = std.ArrayList(u8).init(comp.gpa),
135 .poisoned_identifiers = std.StringHashMap(void).init(comp.gpa),
136 .top_expansion_buf = ExpandBuf.init(comp.gpa),
137 .hideset = .{ .comp = comp },
138 };
139 comp.pragmaEvent(.before_preprocess);
140 return pp;
141}
142
143/// Initialize Preprocessor with builtin macros.
144pub fn initDefault(comp: *Compilation) !Preprocessor {
145 var pp = init(comp);
146 errdefer pp.deinit();
147 try pp.addBuiltinMacros();
148 return pp;
149}
150
151const builtin_macros = struct {
152 const args = [1][]const u8{"X"};
153
154 const has_attribute = [1]RawToken{.{
155 .id = .macro_param_has_attribute,
156 .source = .generated,
157 }};
158 const has_c_attribute = [1]RawToken{.{
159 .id = .macro_param_has_c_attribute,
160 .source = .generated,
161 }};
162 const has_declspec_attribute = [1]RawToken{.{
163 .id = .macro_param_has_declspec_attribute,
164 .source = .generated,
165 }};
166 const has_warning = [1]RawToken{.{
167 .id = .macro_param_has_warning,
168 .source = .generated,
169 }};
170 const has_feature = [1]RawToken{.{
171 .id = .macro_param_has_feature,
172 .source = .generated,
173 }};
174 const has_extension = [1]RawToken{.{
175 .id = .macro_param_has_extension,
176 .source = .generated,
177 }};
178 const has_builtin = [1]RawToken{.{
179 .id = .macro_param_has_builtin,
180 .source = .generated,
181 }};
182 const has_include = [1]RawToken{.{
183 .id = .macro_param_has_include,
184 .source = .generated,
185 }};
186 const has_include_next = [1]RawToken{.{
187 .id = .macro_param_has_include_next,
188 .source = .generated,
189 }};
190 const has_embed = [1]RawToken{.{
191 .id = .macro_param_has_embed,
192 .source = .generated,
193 }};
194
195 const is_identifier = [1]RawToken{.{
196 .id = .macro_param_is_identifier,
197 .source = .generated,
198 }};
199
200 const pragma_operator = [1]RawToken{.{
201 .id = .macro_param_pragma_operator,
202 .source = .generated,
203 }};
204
205 const file = [1]RawToken{.{
206 .id = .macro_file,
207 .source = .generated,
208 }};
209 const line = [1]RawToken{.{
210 .id = .macro_line,
211 .source = .generated,
212 }};
213 const counter = [1]RawToken{.{
214 .id = .macro_counter,
215 .source = .generated,
216 }};
217};
218
219fn addBuiltinMacro(pp: *Preprocessor, name: []const u8, is_func: bool, tokens: []const RawToken) !void {
220 try pp.defines.putNoClobber(pp.gpa, name, .{
221 .params = &builtin_macros.args,
222 .tokens = tokens,
223 .var_args = false,
224 .is_func = is_func,
225 .loc = .{ .id = .generated },
226 .is_builtin = true,
227 });
228}
229
230pub fn addBuiltinMacros(pp: *Preprocessor) !void {
231 try pp.addBuiltinMacro("__has_attribute", true, &builtin_macros.has_attribute);
232 try pp.addBuiltinMacro("__has_c_attribute", true, &builtin_macros.has_c_attribute);
233 try pp.addBuiltinMacro("__has_declspec_attribute", true, &builtin_macros.has_declspec_attribute);
234 try pp.addBuiltinMacro("__has_warning", true, &builtin_macros.has_warning);
235 try pp.addBuiltinMacro("__has_feature", true, &builtin_macros.has_feature);
236 try pp.addBuiltinMacro("__has_extension", true, &builtin_macros.has_extension);
237 try pp.addBuiltinMacro("__has_builtin", true, &builtin_macros.has_builtin);
238 try pp.addBuiltinMacro("__has_include", true, &builtin_macros.has_include);
239 try pp.addBuiltinMacro("__has_include_next", true, &builtin_macros.has_include_next);
240 try pp.addBuiltinMacro("__has_embed", true, &builtin_macros.has_embed);
241 try pp.addBuiltinMacro("__is_identifier", true, &builtin_macros.is_identifier);
242 try pp.addBuiltinMacro("_Pragma", true, &builtin_macros.pragma_operator);
243
244 try pp.addBuiltinMacro("__FILE__", false, &builtin_macros.file);
245 try pp.addBuiltinMacro("__LINE__", false, &builtin_macros.line);
246 try pp.addBuiltinMacro("__COUNTER__", false, &builtin_macros.counter);
247}
248
249pub fn deinit(pp: *Preprocessor) void {
250 pp.defines.deinit(pp.gpa);
251 pp.tokens.deinit(pp.gpa);
252 pp.arena.deinit();
253 pp.token_buf.deinit();
254 pp.char_buf.deinit();
255 pp.poisoned_identifiers.deinit();
256 pp.include_guards.deinit(pp.gpa);
257 pp.top_expansion_buf.deinit();
258 pp.hideset.deinit();
259 for (pp.expansion_entries.items(.locs)) |locs| TokenWithExpansionLocs.free(locs, pp.gpa);
260 pp.expansion_entries.deinit(pp.gpa);
261}
262
263/// Free buffers that are not needed after preprocessing
264fn clearBuffers(pp: *Preprocessor) void {
265 pp.token_buf.clearAndFree();
266 pp.char_buf.clearAndFree();
267 pp.top_expansion_buf.clearAndFree();
268 pp.hideset.clearAndFree();
269}
270
271pub fn expansionSlice(pp: *Preprocessor, tok: Tree.TokenIndex) []Source.Location {
272 const S = struct {
273 fn orderTokenIndex(context: Tree.TokenIndex, item: Tree.TokenIndex) std.math.Order {
274 return std.math.order(context, item);
275 }
276 };
277
278 const indices = pp.expansion_entries.items(.idx);
279 const idx = std.sort.binarySearch(Tree.TokenIndex, indices, tok, S.orderTokenIndex) orelse return &.{};
280 const locs = pp.expansion_entries.items(.locs)[idx];
281 var i: usize = 0;
282 while (locs[i].id != .unused) : (i += 1) {}
283 return locs[0..i];
284}
285
286/// Preprocess a compilation unit of sources into a parsable list of tokens.
287pub fn preprocessSources(pp: *Preprocessor, sources: []const Source) Error!void {
288 assert(sources.len > 1);
289 const first = sources[0];
290 try pp.addIncludeStart(first);
291 for (sources[1..]) |header| {
292 try pp.addIncludeStart(header);
293 _ = try pp.preprocess(header);
294 }
295 try pp.addIncludeResume(first.id, 0, 1);
296 const eof = try pp.preprocess(first);
297 try pp.addToken(eof);
298 pp.clearBuffers();
299}
300
301/// Preprocess a source file, returns eof token.
302pub fn preprocess(pp: *Preprocessor, source: Source) Error!TokenWithExpansionLocs {
303 const eof = pp.preprocessExtra(source) catch |er| switch (er) {
304 // This cannot occur in the main file and is handled in `include`.
305 error.StopPreprocessing => unreachable,
306 else => |e| return e,
307 };
308 try eof.checkMsEof(source, pp.comp);
309 return eof;
310}
311
312/// Tokenize a file without any preprocessing, returns eof token.
313pub fn tokenize(pp: *Preprocessor, source: Source) Error!Token {
314 assert(pp.linemarkers == .none);
315 assert(pp.preserve_whitespace == false);
316 var tokenizer = Tokenizer{
317 .buf = source.buf,
318 .comp = pp.comp,
319 .source = source.id,
320 };
321
322 // Estimate how many new tokens this source will contain.
323 const estimated_token_count = source.buf.len / 8;
324 try pp.ensureTotalTokenCapacity(pp.tokens.len + estimated_token_count);
325
326 while (true) {
327 const tok = tokenizer.next();
328 if (tok.id == .eof) return tokFromRaw(tok);
329 try pp.addToken(tokFromRaw(tok));
330 }
331}
332
333pub fn addIncludeStart(pp: *Preprocessor, source: Source) !void {
334 if (pp.linemarkers == .none) return;
335 try pp.addToken(.{ .id = .include_start, .loc = .{
336 .id = source.id,
337 .byte_offset = std.math.maxInt(u32),
338 .line = 1,
339 } });
340}
341
342pub fn addIncludeResume(pp: *Preprocessor, source: Source.Id, offset: u32, line: u32) !void {
343 if (pp.linemarkers == .none) return;
344 try pp.addToken(.{ .id = .include_resume, .loc = .{
345 .id = source,
346 .byte_offset = offset,
347 .line = line,
348 } });
349}
350
351fn invalidTokenDiagnostic(tok_id: Token.Id) Diagnostics.Tag {
352 return switch (tok_id) {
353 .unterminated_string_literal => .unterminated_string_literal_warning,
354 .empty_char_literal => .empty_char_literal_warning,
355 .unterminated_char_literal => .unterminated_char_literal_warning,
356 else => unreachable,
357 };
358}
359
360/// Return the name of the #ifndef guard macro that starts a source, if any.
361fn findIncludeGuard(pp: *Preprocessor, source: Source) ?[]const u8 {
362 var tokenizer = Tokenizer{
363 .buf = source.buf,
364 .langopts = pp.comp.langopts,
365 .source = source.id,
366 };
367 var hash = tokenizer.nextNoWS();
368 while (hash.id == .nl) hash = tokenizer.nextNoWS();
369 if (hash.id != .hash) return null;
370 const ifndef = tokenizer.nextNoWS();
371 if (ifndef.id != .keyword_ifndef) return null;
372 const guard = tokenizer.nextNoWS();
373 if (guard.id != .identifier) return null;
374 return pp.tokSlice(guard);
375}
376
377fn preprocessExtra(pp: *Preprocessor, source: Source) MacroError!TokenWithExpansionLocs {
378 var guard_name = pp.findIncludeGuard(source);
379
380 pp.preprocess_count += 1;
381 var tokenizer = Tokenizer{
382 .buf = source.buf,
383 .langopts = pp.comp.langopts,
384 .source = source.id,
385 };
386
387 // Estimate how many new tokens this source will contain.
388 const estimated_token_count = source.buf.len / 8;
389 try pp.ensureTotalTokenCapacity(pp.tokens.len + estimated_token_count);
390
391 var if_level: u8 = 0;
392 var if_kind: [64]u8 = .{0} ** 64;
393 const until_else = 0;
394 const until_endif = 1;
395 const until_endif_seen_else = 2;
396
397 var start_of_line = true;
398 while (true) {
399 var tok = tokenizer.next();
400 switch (tok.id) {
401 .hash => if (!start_of_line) try pp.addToken(tokFromRaw(tok)) else {
402 const directive = tokenizer.nextNoWS();
403 switch (directive.id) {
404 .keyword_error, .keyword_warning => {
405 // #error tokens..
406 pp.top_expansion_buf.items.len = 0;
407 const char_top = pp.char_buf.items.len;
408 defer pp.char_buf.items.len = char_top;
409
410 while (true) {
411 tok = tokenizer.next();
412 if (tok.id == .nl or tok.id == .eof) break;
413 if (tok.id == .whitespace) tok.id = .macro_ws;
414 try pp.top_expansion_buf.append(tokFromRaw(tok));
415 }
416 try pp.stringify(pp.top_expansion_buf.items);
417 const slice = pp.char_buf.items[char_top + 1 .. pp.char_buf.items.len - 2];
418 const duped = try pp.comp.diagnostics.arena.allocator().dupe(u8, slice);
419
420 try pp.comp.addDiagnostic(.{
421 .tag = if (directive.id == .keyword_error) .error_directive else .warning_directive,
422 .loc = .{ .id = tok.source, .byte_offset = directive.start, .line = directive.line },
423 .extra = .{ .str = duped },
424 }, &.{});
425 },
426 .keyword_if => {
427 const sum, const overflowed = @addWithOverflow(if_level, 1);
428 if (overflowed != 0)
429 return pp.fatal(directive, "too many #if nestings", .{});
430 if_level = sum;
431
432 if (try pp.expr(&tokenizer)) {
433 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
434 if (pp.verbose) {
435 pp.verboseLog(directive, "entering then branch of #if", .{});
436 }
437 } else {
438 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
439 try pp.skip(&tokenizer, .until_else);
440 if (pp.verbose) {
441 pp.verboseLog(directive, "entering else branch of #if", .{});
442 }
443 }
444 },
445 .keyword_ifdef => {
446 const sum, const overflowed = @addWithOverflow(if_level, 1);
447 if (overflowed != 0)
448 return pp.fatal(directive, "too many #if nestings", .{});
449 if_level = sum;
450
451 const macro_name = (try pp.expectMacroName(&tokenizer)) orelse continue;
452 try pp.expectNl(&tokenizer);
453 if (pp.defines.get(macro_name) != null) {
454 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
455 if (pp.verbose) {
456 pp.verboseLog(directive, "entering then branch of #ifdef", .{});
457 }
458 } else {
459 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
460 try pp.skip(&tokenizer, .until_else);
461 if (pp.verbose) {
462 pp.verboseLog(directive, "entering else branch of #ifdef", .{});
463 }
464 }
465 },
466 .keyword_ifndef => {
467 const sum, const overflowed = @addWithOverflow(if_level, 1);
468 if (overflowed != 0)
469 return pp.fatal(directive, "too many #if nestings", .{});
470 if_level = sum;
471
472 const macro_name = (try pp.expectMacroName(&tokenizer)) orelse continue;
473 try pp.expectNl(&tokenizer);
474 if (pp.defines.get(macro_name) == null) {
475 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
476 } else {
477 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
478 try pp.skip(&tokenizer, .until_else);
479 }
480 },
481 .keyword_elif => {
482 if (if_level == 0) {
483 try pp.err(directive, .elif_without_if);
484 if_level += 1;
485 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
486 } else if (if_level == 1) {
487 guard_name = null;
488 }
489 switch (std.mem.readPackedIntNative(u2, &if_kind, if_level * 2)) {
490 until_else => if (try pp.expr(&tokenizer)) {
491 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
492 if (pp.verbose) {
493 pp.verboseLog(directive, "entering then branch of #elif", .{});
494 }
495 } else {
496 try pp.skip(&tokenizer, .until_else);
497 if (pp.verbose) {
498 pp.verboseLog(directive, "entering else branch of #elif", .{});
499 }
500 },
501 until_endif => try pp.skip(&tokenizer, .until_endif),
502 until_endif_seen_else => {
503 try pp.err(directive, .elif_after_else);
504 skipToNl(&tokenizer);
505 },
506 else => unreachable,
507 }
508 },
509 .keyword_elifdef => {
510 if (if_level == 0) {
511 try pp.err(directive, .elifdef_without_if);
512 if_level += 1;
513 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
514 } else if (if_level == 1) {
515 guard_name = null;
516 }
517 switch (std.mem.readPackedIntNative(u2, &if_kind, if_level * 2)) {
518 until_else => {
519 const macro_name = try pp.expectMacroName(&tokenizer);
520 if (macro_name == null) {
521 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
522 try pp.skip(&tokenizer, .until_else);
523 if (pp.verbose) {
524 pp.verboseLog(directive, "entering else branch of #elifdef", .{});
525 }
526 } else {
527 try pp.expectNl(&tokenizer);
528 if (pp.defines.get(macro_name.?) != null) {
529 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
530 if (pp.verbose) {
531 pp.verboseLog(directive, "entering then branch of #elifdef", .{});
532 }
533 } else {
534 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
535 try pp.skip(&tokenizer, .until_else);
536 if (pp.verbose) {
537 pp.verboseLog(directive, "entering else branch of #elifdef", .{});
538 }
539 }
540 }
541 },
542 until_endif => try pp.skip(&tokenizer, .until_endif),
543 until_endif_seen_else => {
544 try pp.err(directive, .elifdef_after_else);
545 skipToNl(&tokenizer);
546 },
547 else => unreachable,
548 }
549 },
550 .keyword_elifndef => {
551 if (if_level == 0) {
552 try pp.err(directive, .elifdef_without_if);
553 if_level += 1;
554 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
555 } else if (if_level == 1) {
556 guard_name = null;
557 }
558 switch (std.mem.readPackedIntNative(u2, &if_kind, if_level * 2)) {
559 until_else => {
560 const macro_name = try pp.expectMacroName(&tokenizer);
561 if (macro_name == null) {
562 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
563 try pp.skip(&tokenizer, .until_else);
564 if (pp.verbose) {
565 pp.verboseLog(directive, "entering else branch of #elifndef", .{});
566 }
567 } else {
568 try pp.expectNl(&tokenizer);
569 if (pp.defines.get(macro_name.?) == null) {
570 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif);
571 if (pp.verbose) {
572 pp.verboseLog(directive, "entering then branch of #elifndef", .{});
573 }
574 } else {
575 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_else);
576 try pp.skip(&tokenizer, .until_else);
577 if (pp.verbose) {
578 pp.verboseLog(directive, "entering else branch of #elifndef", .{});
579 }
580 }
581 }
582 },
583 until_endif => try pp.skip(&tokenizer, .until_endif),
584 until_endif_seen_else => {
585 try pp.err(directive, .elifdef_after_else);
586 skipToNl(&tokenizer);
587 },
588 else => unreachable,
589 }
590 },
591 .keyword_else => {
592 try pp.expectNl(&tokenizer);
593 if (if_level == 0) {
594 try pp.err(directive, .else_without_if);
595 continue;
596 } else if (if_level == 1) {
597 guard_name = null;
598 }
599 switch (std.mem.readPackedIntNative(u2, &if_kind, if_level * 2)) {
600 until_else => {
601 std.mem.writePackedIntNative(u2, &if_kind, if_level * 2, until_endif_seen_else);
602 if (pp.verbose) {
603 pp.verboseLog(directive, "#else branch here", .{});
604 }
605 },
606 until_endif => try pp.skip(&tokenizer, .until_endif_seen_else),
607 until_endif_seen_else => {
608 try pp.err(directive, .else_after_else);
609 skipToNl(&tokenizer);
610 },
611 else => unreachable,
612 }
613 },
614 .keyword_endif => {
615 try pp.expectNl(&tokenizer);
616 if (if_level == 0) {
617 guard_name = null;
618 try pp.err(directive, .endif_without_if);
619 continue;
620 } else if (if_level == 1) {
621 const saved_tokenizer = tokenizer;
622 defer tokenizer = saved_tokenizer;
623
624 var next = tokenizer.nextNoWS();
625 while (next.id == .nl) : (next = tokenizer.nextNoWS()) {}
626 if (next.id != .eof) guard_name = null;
627 }
628 if_level -= 1;
629 },
630 .keyword_define => try pp.define(&tokenizer, directive),
631 .keyword_undef => {
632 const macro_name = (try pp.expectMacroName(&tokenizer)) orelse continue;
633 if (pp.store_macro_tokens) {
634 try pp.addToken(tokFromRaw(directive));
635 }
636
637 _ = pp.defines.remove(macro_name);
638 try pp.expectNl(&tokenizer);
639 },
640 .keyword_include => {
641 try pp.include(&tokenizer, .first);
642 continue;
643 },
644 .keyword_include_next => {
645 try pp.comp.addDiagnostic(.{
646 .tag = .include_next,
647 .loc = .{ .id = tok.source, .byte_offset = directive.start, .line = directive.line },
648 }, &.{});
649 if (pp.include_depth == 0) {
650 try pp.comp.addDiagnostic(.{
651 .tag = .include_next_outside_header,
652 .loc = .{ .id = tok.source, .byte_offset = directive.start, .line = directive.line },
653 }, &.{});
654 try pp.include(&tokenizer, .first);
655 } else {
656 try pp.include(&tokenizer, .next);
657 }
658 },
659 .keyword_embed => try pp.embed(&tokenizer),
660 .keyword_pragma => {
661 try pp.pragma(&tokenizer, directive, null, &.{});
662 continue;
663 },
664 .keyword_line => {
665 // #line number "file"
666 const digits = tokenizer.nextNoWS();
667 if (digits.id != .pp_num) try pp.err(digits, .line_simple_digit);
668 // TODO: validate that the pp_num token is solely digits
669
670 if (digits.id == .eof or digits.id == .nl) continue;
671 const name = tokenizer.nextNoWS();
672 if (name.id == .eof or name.id == .nl) continue;
673 if (name.id != .string_literal) try pp.err(name, .line_invalid_filename);
674 try pp.expectNl(&tokenizer);
675 },
676 .pp_num => {
677 // # number "file" flags
678 // TODO: validate that the pp_num token is solely digits
679 // if not, emit `GNU line marker directive requires a simple digit sequence`
680 const name = tokenizer.nextNoWS();
681 if (name.id == .eof or name.id == .nl) continue;
682 if (name.id != .string_literal) try pp.err(name, .line_invalid_filename);
683
684 const flag_1 = tokenizer.nextNoWS();
685 if (flag_1.id == .eof or flag_1.id == .nl) continue;
686 const flag_2 = tokenizer.nextNoWS();
687 if (flag_2.id == .eof or flag_2.id == .nl) continue;
688 const flag_3 = tokenizer.nextNoWS();
689 if (flag_3.id == .eof or flag_3.id == .nl) continue;
690 const flag_4 = tokenizer.nextNoWS();
691 if (flag_4.id == .eof or flag_4.id == .nl) continue;
692 try pp.expectNl(&tokenizer);
693 },
694 .nl => {},
695 .eof => {
696 if (if_level != 0) try pp.err(tok, .unterminated_conditional_directive);
697 return tokFromRaw(directive);
698 },
699 else => {
700 try pp.err(tok, .invalid_preprocessing_directive);
701 skipToNl(&tokenizer);
702 },
703 }
704 if (pp.preserve_whitespace) {
705 tok.id = .nl;
706 try pp.addToken(tokFromRaw(tok));
707 }
708 },
709 .whitespace => if (pp.preserve_whitespace) try pp.addToken(tokFromRaw(tok)),
710 .nl => {
711 start_of_line = true;
712 if (pp.preserve_whitespace) try pp.addToken(tokFromRaw(tok));
713 },
714 .eof => {
715 if (if_level != 0) try pp.err(tok, .unterminated_conditional_directive);
716 // The following check needs to occur here and not at the top of the function
717 // because a pragma may change the level during preprocessing
718 if (source.buf.len > 0 and source.buf[source.buf.len - 1] != '\n') {
719 try pp.err(tok, .newline_eof);
720 }
721 if (guard_name) |name| {
722 if (try pp.include_guards.fetchPut(pp.gpa, source.id, name)) |prev| {
723 assert(mem.eql(u8, name, prev.value));
724 }
725 }
726 return tokFromRaw(tok);
727 },
728 .unterminated_string_literal, .unterminated_char_literal, .empty_char_literal => |tag| {
729 start_of_line = false;
730 try pp.err(tok, invalidTokenDiagnostic(tag));
731 try pp.expandMacro(&tokenizer, tok);
732 },
733 .unterminated_comment => try pp.err(tok, .unterminated_comment),
734 else => {
735 if (tok.id.isMacroIdentifier() and pp.poisoned_identifiers.get(pp.tokSlice(tok)) != null) {
736 try pp.err(tok, .poisoned_identifier);
737 }
738 // Add the token to the buffer doing any necessary expansions.
739 start_of_line = false;
740 try pp.expandMacro(&tokenizer, tok);
741 },
742 }
743 }
744}
745
746/// Get raw token source string.
747/// Returned slice is invalidated when comp.generated_buf is updated.
748pub fn tokSlice(pp: *Preprocessor, token: anytype) []const u8 {
749 if (token.id.lexeme()) |some| return some;
750 const source = pp.comp.getSource(token.source);
751 return source.buf[token.start..token.end];
752}
753
754/// Convert a token from the Tokenizer into a token used by the parser.
755fn tokFromRaw(raw: RawToken) TokenWithExpansionLocs {
756 return .{
757 .id = raw.id,
758 .loc = .{
759 .id = raw.source,
760 .byte_offset = raw.start,
761 .line = raw.line,
762 },
763 };
764}
765
766fn err(pp: *Preprocessor, raw: RawToken, tag: Diagnostics.Tag) !void {
767 try pp.comp.addDiagnostic(.{
768 .tag = tag,
769 .loc = .{
770 .id = raw.source,
771 .byte_offset = raw.start,
772 .line = raw.line,
773 },
774 }, &.{});
775}
776
777fn errStr(pp: *Preprocessor, tok: TokenWithExpansionLocs, tag: Diagnostics.Tag, str: []const u8) !void {
778 try pp.comp.addDiagnostic(.{
779 .tag = tag,
780 .loc = tok.loc,
781 .extra = .{ .str = str },
782 }, tok.expansionSlice());
783}
784
785fn fatal(pp: *Preprocessor, raw: RawToken, comptime fmt: []const u8, args: anytype) Compilation.Error {
786 try pp.comp.diagnostics.list.append(pp.gpa, .{
787 .tag = .cli_error,
788 .kind = .@"fatal error",
789 .extra = .{ .str = try std.fmt.allocPrint(pp.comp.diagnostics.arena.allocator(), fmt, args) },
790 .loc = .{
791 .id = raw.source,
792 .byte_offset = raw.start,
793 .line = raw.line,
794 },
795 });
796 return error.FatalError;
797}
798
799fn fatalNotFound(pp: *Preprocessor, tok: TokenWithExpansionLocs, filename: []const u8) Compilation.Error {
800 const old = pp.comp.diagnostics.fatal_errors;
801 pp.comp.diagnostics.fatal_errors = true;
802 defer pp.comp.diagnostics.fatal_errors = old;
803
804 try pp.comp.diagnostics.addExtra(pp.comp.langopts, .{ .tag = .cli_error, .loc = tok.loc, .extra = .{
805 .str = try std.fmt.allocPrint(pp.comp.diagnostics.arena.allocator(), "'{s}' not found", .{filename}),
806 } }, tok.expansionSlice(), false);
807 unreachable; // addExtra should've returned FatalError
808}
809
810fn verboseLog(pp: *Preprocessor, raw: RawToken, comptime fmt: []const u8, args: anytype) void {
811 const source = pp.comp.getSource(raw.source);
812 const line_col = source.lineCol(.{ .id = raw.source, .line = raw.line, .byte_offset = raw.start });
813
814 const stderr = std.io.getStdErr().writer();
815 var buf_writer = std.io.bufferedWriter(stderr);
816 const writer = buf_writer.writer();
817 defer buf_writer.flush() catch {};
818 writer.print("{s}:{d}:{d}: ", .{ source.path, line_col.line_no, line_col.col }) catch return;
819 writer.print(fmt, args) catch return;
820 writer.writeByte('\n') catch return;
821 writer.writeAll(line_col.line) catch return;
822 writer.writeByte('\n') catch return;
823}
824
825/// Consume next token, error if it is not an identifier.
826fn expectMacroName(pp: *Preprocessor, tokenizer: *Tokenizer) Error!?[]const u8 {
827 const macro_name = tokenizer.nextNoWS();
828 if (!macro_name.id.isMacroIdentifier()) {
829 try pp.err(macro_name, .macro_name_missing);
830 skipToNl(tokenizer);
831 return null;
832 }
833 return pp.tokSlice(macro_name);
834}
835
836/// Skip until after a newline, error if extra tokens before it.
837fn expectNl(pp: *Preprocessor, tokenizer: *Tokenizer) Error!void {
838 var sent_err = false;
839 while (true) {
840 const tok = tokenizer.next();
841 if (tok.id == .nl or tok.id == .eof) return;
842 if (tok.id == .whitespace or tok.id == .comment) continue;
843 if (!sent_err) {
844 sent_err = true;
845 try pp.err(tok, .extra_tokens_directive_end);
846 }
847 }
848}
849
850fn getTokenState(pp: *const Preprocessor) TokenState {
851 return .{
852 .tokens_len = pp.tokens.len,
853 .expansion_entries_len = pp.expansion_entries.len,
854 };
855}
856
857fn restoreTokenState(pp: *Preprocessor, state: TokenState) void {
858 pp.tokens.len = state.tokens_len;
859 pp.expansion_entries.len = state.expansion_entries_len;
860}
861
862/// Consume all tokens until a newline and parse the result into a boolean.
863fn expr(pp: *Preprocessor, tokenizer: *Tokenizer) MacroError!bool {
864 const token_state = pp.getTokenState();
865 defer {
866 for (pp.top_expansion_buf.items) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
867 pp.restoreTokenState(token_state);
868 }
869
870 pp.top_expansion_buf.items.len = 0;
871 const eof = while (true) {
872 const tok = tokenizer.next();
873 switch (tok.id) {
874 .nl, .eof => break tok,
875 .whitespace => if (pp.top_expansion_buf.items.len == 0) continue,
876 else => {},
877 }
878 try pp.top_expansion_buf.append(tokFromRaw(tok));
879 } else unreachable;
880 if (pp.top_expansion_buf.items.len != 0) {
881 pp.expansion_source_loc = pp.top_expansion_buf.items[0].loc;
882 pp.hideset.clearRetainingCapacity();
883 try pp.expandMacroExhaustive(tokenizer, &pp.top_expansion_buf, 0, pp.top_expansion_buf.items.len, false, .expr);
884 }
885 for (pp.top_expansion_buf.items) |tok| {
886 if (tok.id == .macro_ws) continue;
887 if (!tok.id.validPreprocessorExprStart()) {
888 try pp.comp.addDiagnostic(.{
889 .tag = .invalid_preproc_expr_start,
890 .loc = tok.loc,
891 }, tok.expansionSlice());
892 return false;
893 }
894 break;
895 } else {
896 try pp.err(eof, .expected_value_in_expr);
897 return false;
898 }
899
900 // validate the tokens in the expression
901 try pp.ensureUnusedTokenCapacity(pp.top_expansion_buf.items.len);
902 var i: usize = 0;
903 const items = pp.top_expansion_buf.items;
904 while (i < items.len) : (i += 1) {
905 var tok = items[i];
906 switch (tok.id) {
907 .string_literal,
908 .string_literal_utf_16,
909 .string_literal_utf_8,
910 .string_literal_utf_32,
911 .string_literal_wide,
912 => {
913 try pp.comp.addDiagnostic(.{
914 .tag = .string_literal_in_pp_expr,
915 .loc = tok.loc,
916 }, tok.expansionSlice());
917 return false;
918 },
919 .plus_plus,
920 .minus_minus,
921 .plus_equal,
922 .minus_equal,
923 .asterisk_equal,
924 .slash_equal,
925 .percent_equal,
926 .angle_bracket_angle_bracket_left_equal,
927 .angle_bracket_angle_bracket_right_equal,
928 .ampersand_equal,
929 .caret_equal,
930 .pipe_equal,
931 .l_bracket,
932 .r_bracket,
933 .l_brace,
934 .r_brace,
935 .ellipsis,
936 .semicolon,
937 .hash,
938 .hash_hash,
939 .equal,
940 .arrow,
941 .period,
942 => {
943 try pp.comp.addDiagnostic(.{
944 .tag = .invalid_preproc_operator,
945 .loc = tok.loc,
946 }, tok.expansionSlice());
947 return false;
948 },
949 .macro_ws, .whitespace => continue,
950 .keyword_false => tok.id = .zero,
951 .keyword_true => tok.id = .one,
952 else => if (tok.id.isMacroIdentifier()) {
953 if (tok.id == .keyword_defined) {
954 const tokens_consumed = try pp.handleKeywordDefined(&tok, items[i + 1 ..], eof);
955 i += tokens_consumed;
956 } else {
957 try pp.errStr(tok, .undefined_macro, pp.expandedSlice(tok));
958
959 if (i + 1 < pp.top_expansion_buf.items.len and
960 pp.top_expansion_buf.items[i + 1].id == .l_paren)
961 {
962 try pp.errStr(tok, .fn_macro_undefined, pp.expandedSlice(tok));
963 return false;
964 }
965
966 tok.id = .zero; // undefined macro
967 }
968 },
969 }
970 pp.addTokenAssumeCapacity(tok);
971 }
972 try pp.addToken(.{
973 .id = .eof,
974 .loc = tokFromRaw(eof).loc,
975 });
976
977 // Actually parse it.
978 var parser = Parser{
979 .pp = pp,
980 .comp = pp.comp,
981 .gpa = pp.gpa,
982 .tok_ids = pp.tokens.items(.id),
983 .tok_i = @intCast(token_state.tokens_len),
984 .arena = pp.arena.allocator(),
985 .in_macro = true,
986 .strings = std.ArrayListAligned(u8, 4).init(pp.comp.gpa),
987
988 .data = undefined,
989 .value_map = undefined,
990 .labels = undefined,
991 .decl_buf = undefined,
992 .list_buf = undefined,
993 .param_buf = undefined,
994 .enum_buf = undefined,
995 .record_buf = undefined,
996 .attr_buf = undefined,
997 .field_attr_buf = undefined,
998 .string_ids = undefined,
999 };
1000 defer parser.strings.deinit();
1001 return parser.macroExpr();
1002}
1003
1004/// Turns macro_tok from .keyword_defined into .zero or .one depending on whether the argument is defined
1005/// Returns the number of tokens consumed
1006fn handleKeywordDefined(pp: *Preprocessor, macro_tok: *TokenWithExpansionLocs, tokens: []const TokenWithExpansionLocs, eof: RawToken) !usize {
1007 std.debug.assert(macro_tok.id == .keyword_defined);
1008 var it = TokenIterator.init(tokens);
1009 const first = it.nextNoWS() orelse {
1010 try pp.err(eof, .macro_name_missing);
1011 return it.i;
1012 };
1013 switch (first.id) {
1014 .l_paren => {},
1015 else => {
1016 if (!first.id.isMacroIdentifier()) {
1017 try pp.errStr(first, .macro_name_must_be_identifier, pp.expandedSlice(first));
1018 }
1019 macro_tok.id = if (pp.defines.contains(pp.expandedSlice(first))) .one else .zero;
1020 return it.i;
1021 },
1022 }
1023 const second = it.nextNoWS() orelse {
1024 try pp.err(eof, .macro_name_missing);
1025 return it.i;
1026 };
1027 if (!second.id.isMacroIdentifier()) {
1028 try pp.comp.addDiagnostic(.{
1029 .tag = .macro_name_must_be_identifier,
1030 .loc = second.loc,
1031 }, second.expansionSlice());
1032 return it.i;
1033 }
1034 macro_tok.id = if (pp.defines.contains(pp.expandedSlice(second))) .one else .zero;
1035
1036 const last = it.nextNoWS();
1037 if (last == null or last.?.id != .r_paren) {
1038 const tok = last orelse tokFromRaw(eof);
1039 try pp.comp.addDiagnostic(.{
1040 .tag = .closing_paren,
1041 .loc = tok.loc,
1042 }, tok.expansionSlice());
1043 try pp.comp.addDiagnostic(.{
1044 .tag = .to_match_paren,
1045 .loc = first.loc,
1046 }, first.expansionSlice());
1047 }
1048
1049 return it.i;
1050}
1051
1052/// Skip until #else #elif #endif, return last directive token id.
1053/// Also skips nested #if ... #endifs.
1054fn skip(
1055 pp: *Preprocessor,
1056 tokenizer: *Tokenizer,
1057 cont: enum { until_else, until_endif, until_endif_seen_else },
1058) Error!void {
1059 var ifs_seen: u32 = 0;
1060 var line_start = true;
1061 while (tokenizer.index < tokenizer.buf.len) {
1062 if (line_start) {
1063 const saved_tokenizer = tokenizer.*;
1064 const hash = tokenizer.nextNoWS();
1065 if (hash.id == .nl) continue;
1066 line_start = false;
1067 if (hash.id != .hash) continue;
1068 const directive = tokenizer.nextNoWS();
1069 switch (directive.id) {
1070 .keyword_else => {
1071 if (ifs_seen != 0) continue;
1072 if (cont == .until_endif_seen_else) {
1073 try pp.err(directive, .else_after_else);
1074 continue;
1075 }
1076 tokenizer.* = saved_tokenizer;
1077 return;
1078 },
1079 .keyword_elif => {
1080 if (ifs_seen != 0 or cont == .until_endif) continue;
1081 if (cont == .until_endif_seen_else) {
1082 try pp.err(directive, .elif_after_else);
1083 continue;
1084 }
1085 tokenizer.* = saved_tokenizer;
1086 return;
1087 },
1088 .keyword_elifdef => {
1089 if (ifs_seen != 0 or cont == .until_endif) continue;
1090 if (cont == .until_endif_seen_else) {
1091 try pp.err(directive, .elifdef_after_else);
1092 continue;
1093 }
1094 tokenizer.* = saved_tokenizer;
1095 return;
1096 },
1097 .keyword_elifndef => {
1098 if (ifs_seen != 0 or cont == .until_endif) continue;
1099 if (cont == .until_endif_seen_else) {
1100 try pp.err(directive, .elifndef_after_else);
1101 continue;
1102 }
1103 tokenizer.* = saved_tokenizer;
1104 return;
1105 },
1106 .keyword_endif => {
1107 if (ifs_seen == 0) {
1108 tokenizer.* = saved_tokenizer;
1109 return;
1110 }
1111 ifs_seen -= 1;
1112 },
1113 .keyword_if, .keyword_ifdef, .keyword_ifndef => ifs_seen += 1,
1114 else => {},
1115 }
1116 } else if (tokenizer.buf[tokenizer.index] == '\n') {
1117 line_start = true;
1118 tokenizer.index += 1;
1119 tokenizer.line += 1;
1120 if (pp.preserve_whitespace) {
1121 try pp.addToken(.{ .id = .nl, .loc = .{
1122 .id = tokenizer.source,
1123 .line = tokenizer.line,
1124 } });
1125 }
1126 } else {
1127 line_start = false;
1128 tokenizer.index += 1;
1129 }
1130 } else {
1131 const eof = tokenizer.next();
1132 return pp.err(eof, .unterminated_conditional_directive);
1133 }
1134}
1135
1136// Skip until newline, ignore other tokens.
1137fn skipToNl(tokenizer: *Tokenizer) void {
1138 while (true) {
1139 const tok = tokenizer.next();
1140 if (tok.id == .nl or tok.id == .eof) return;
1141 }
1142}
1143
1144const ExpandBuf = std.ArrayList(TokenWithExpansionLocs);
1145fn removePlacemarkers(buf: *ExpandBuf) void {
1146 var i: usize = buf.items.len -% 1;
1147 while (i < buf.items.len) : (i -%= 1) {
1148 if (buf.items[i].id == .placemarker) {
1149 const placemarker = buf.orderedRemove(i);
1150 TokenWithExpansionLocs.free(placemarker.expansion_locs, buf.allocator);
1151 }
1152 }
1153}
1154
1155const MacroArguments = std.ArrayList([]const TokenWithExpansionLocs);
1156fn deinitMacroArguments(allocator: Allocator, args: *const MacroArguments) void {
1157 for (args.items) |item| {
1158 for (item) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, allocator);
1159 allocator.free(item);
1160 }
1161 args.deinit();
1162}
1163
1164fn expandObjMacro(pp: *Preprocessor, simple_macro: *const Macro) Error!ExpandBuf {
1165 var buf = ExpandBuf.init(pp.gpa);
1166 errdefer buf.deinit();
1167 if (simple_macro.tokens.len == 0) {
1168 try buf.append(.{ .id = .placemarker, .loc = .{ .id = .generated } });
1169 return buf;
1170 }
1171 try buf.ensureTotalCapacity(simple_macro.tokens.len);
1172
1173 // Add all of the simple_macros tokens to the new buffer handling any concats.
1174 var i: usize = 0;
1175 while (i < simple_macro.tokens.len) : (i += 1) {
1176 const raw = simple_macro.tokens[i];
1177 const tok = tokFromRaw(raw);
1178 switch (raw.id) {
1179 .hash_hash => {
1180 var rhs = tokFromRaw(simple_macro.tokens[i + 1]);
1181 i += 1;
1182 while (true) {
1183 if (rhs.id == .whitespace) {
1184 rhs = tokFromRaw(simple_macro.tokens[i + 1]);
1185 i += 1;
1186 } else if (rhs.id == .comment and !pp.comp.langopts.preserve_comments_in_macros) {
1187 rhs = tokFromRaw(simple_macro.tokens[i + 1]);
1188 i += 1;
1189 } else break;
1190 }
1191 try pp.pasteTokens(&buf, &.{rhs});
1192 },
1193 .whitespace => if (pp.preserve_whitespace) buf.appendAssumeCapacity(tok),
1194 .macro_file => {
1195 const start = pp.comp.generated_buf.items.len;
1196 const source = pp.comp.getSource(pp.expansion_source_loc.id);
1197 const w = pp.comp.generated_buf.writer(pp.gpa);
1198 try w.print("\"{s}\"\n", .{source.path});
1199
1200 buf.appendAssumeCapacity(try pp.makeGeneratedToken(start, .string_literal, tok));
1201 },
1202 .macro_line => {
1203 const start = pp.comp.generated_buf.items.len;
1204 const source = pp.comp.getSource(pp.expansion_source_loc.id);
1205 const w = pp.comp.generated_buf.writer(pp.gpa);
1206 try w.print("{d}\n", .{source.physicalLine(pp.expansion_source_loc)});
1207
1208 buf.appendAssumeCapacity(try pp.makeGeneratedToken(start, .pp_num, tok));
1209 },
1210 .macro_counter => {
1211 defer pp.counter += 1;
1212 const start = pp.comp.generated_buf.items.len;
1213 const w = pp.comp.generated_buf.writer(pp.gpa);
1214 try w.print("{d}\n", .{pp.counter});
1215
1216 buf.appendAssumeCapacity(try pp.makeGeneratedToken(start, .pp_num, tok));
1217 },
1218 else => buf.appendAssumeCapacity(tok),
1219 }
1220 }
1221
1222 return buf;
1223}
1224
1225/// Join a possibly-parenthesized series of string literal tokens into a single string without
1226/// leading or trailing quotes. The returned slice is invalidated if pp.char_buf changes.
1227/// Returns error.ExpectedStringLiteral if parentheses are not balanced, a non-string-literal
1228/// is encountered, or if no string literals are encountered
1229/// TODO: destringize (replace all '\\' with a single `\` and all '\"' with a '"')
1230fn pasteStringsUnsafe(pp: *Preprocessor, toks: []const TokenWithExpansionLocs) ![]const u8 {
1231 const char_top = pp.char_buf.items.len;
1232 defer pp.char_buf.items.len = char_top;
1233 var unwrapped = toks;
1234 if (toks.len >= 2 and toks[0].id == .l_paren and toks[toks.len - 1].id == .r_paren) {
1235 unwrapped = toks[1 .. toks.len - 1];
1236 }
1237 if (unwrapped.len == 0) return error.ExpectedStringLiteral;
1238
1239 for (unwrapped) |tok| {
1240 if (tok.id == .macro_ws) continue;
1241 if (tok.id != .string_literal) return error.ExpectedStringLiteral;
1242 const str = pp.expandedSlice(tok);
1243 try pp.char_buf.appendSlice(str[1 .. str.len - 1]);
1244 }
1245 return pp.char_buf.items[char_top..];
1246}
1247
1248/// Handle the _Pragma operator (implemented as a builtin macro)
1249fn pragmaOperator(pp: *Preprocessor, arg_tok: TokenWithExpansionLocs, operator_loc: Source.Location) !void {
1250 const arg_slice = pp.expandedSlice(arg_tok);
1251 const content = arg_slice[1 .. arg_slice.len - 1];
1252 const directive = "#pragma ";
1253
1254 pp.char_buf.clearRetainingCapacity();
1255 const total_len = directive.len + content.len + 1; // destringify can never grow the string, + 1 for newline
1256 try pp.char_buf.ensureUnusedCapacity(total_len);
1257 pp.char_buf.appendSliceAssumeCapacity(directive);
1258 pp.destringify(content);
1259 pp.char_buf.appendAssumeCapacity('\n');
1260
1261 const start = pp.comp.generated_buf.items.len;
1262 try pp.comp.generated_buf.appendSlice(pp.gpa, pp.char_buf.items);
1263 var tmp_tokenizer = Tokenizer{
1264 .buf = pp.comp.generated_buf.items,
1265 .langopts = pp.comp.langopts,
1266 .index = @intCast(start),
1267 .source = .generated,
1268 .line = pp.generated_line,
1269 };
1270 pp.generated_line += 1;
1271 const hash_tok = tmp_tokenizer.next();
1272 assert(hash_tok.id == .hash);
1273 const pragma_tok = tmp_tokenizer.next();
1274 assert(pragma_tok.id == .keyword_pragma);
1275 try pp.pragma(&tmp_tokenizer, pragma_tok, operator_loc, arg_tok.expansionSlice());
1276}
1277
1278/// Inverts the output of the preprocessor stringify (#) operation
1279/// (except all whitespace is condensed to a single space)
1280/// writes output to pp.char_buf; assumes capacity is sufficient
1281/// backslash backslash -> backslash
1282/// backslash doublequote -> doublequote
1283/// All other characters remain the same
1284fn destringify(pp: *Preprocessor, str: []const u8) void {
1285 var state: enum { start, backslash_seen } = .start;
1286 for (str) |c| {
1287 switch (c) {
1288 '\\' => {
1289 if (state == .backslash_seen) pp.char_buf.appendAssumeCapacity(c);
1290 state = if (state == .start) .backslash_seen else .start;
1291 },
1292 else => {
1293 if (state == .backslash_seen and c != '"') pp.char_buf.appendAssumeCapacity('\\');
1294 pp.char_buf.appendAssumeCapacity(c);
1295 state = .start;
1296 },
1297 }
1298 }
1299}
1300
1301/// Stringify `tokens` into pp.char_buf.
1302/// See https://gcc.gnu.org/onlinedocs/gcc-11.2.0/cpp/Stringizing.html#Stringizing
1303fn stringify(pp: *Preprocessor, tokens: []const TokenWithExpansionLocs) !void {
1304 try pp.char_buf.append('"');
1305 var ws_state: enum { start, need, not_needed } = .start;
1306 for (tokens) |tok| {
1307 if (tok.id == .macro_ws) {
1308 if (ws_state == .start) continue;
1309 ws_state = .need;
1310 continue;
1311 }
1312 if (ws_state == .need) try pp.char_buf.append(' ');
1313 ws_state = .not_needed;
1314
1315 // backslashes not inside strings are not escaped
1316 const is_str = switch (tok.id) {
1317 .string_literal,
1318 .string_literal_utf_16,
1319 .string_literal_utf_8,
1320 .string_literal_utf_32,
1321 .string_literal_wide,
1322 .char_literal,
1323 .char_literal_utf_16,
1324 .char_literal_utf_32,
1325 .char_literal_wide,
1326 => true,
1327 else => false,
1328 };
1329
1330 for (pp.expandedSlice(tok)) |c| {
1331 if (c == '"')
1332 try pp.char_buf.appendSlice("\\\"")
1333 else if (c == '\\' and is_str)
1334 try pp.char_buf.appendSlice("\\\\")
1335 else
1336 try pp.char_buf.append(c);
1337 }
1338 }
1339 try pp.char_buf.ensureUnusedCapacity(2);
1340 if (pp.char_buf.items[pp.char_buf.items.len - 1] != '\\') {
1341 pp.char_buf.appendSliceAssumeCapacity("\"\n");
1342 return;
1343 }
1344 pp.char_buf.appendAssumeCapacity('"');
1345 var tokenizer: Tokenizer = .{
1346 .buf = pp.char_buf.items,
1347 .index = 0,
1348 .source = .generated,
1349 .langopts = pp.comp.langopts,
1350 .line = 0,
1351 };
1352 const item = tokenizer.next();
1353 if (item.id == .unterminated_string_literal) {
1354 const tok = tokens[tokens.len - 1];
1355 try pp.comp.addDiagnostic(.{
1356 .tag = .invalid_pp_stringify_escape,
1357 .loc = tok.loc,
1358 }, tok.expansionSlice());
1359 pp.char_buf.items.len -= 2; // erase unpaired backslash and appended end quote
1360 pp.char_buf.appendAssumeCapacity('"');
1361 }
1362 pp.char_buf.appendAssumeCapacity('\n');
1363}
1364
1365fn reconstructIncludeString(pp: *Preprocessor, param_toks: []const TokenWithExpansionLocs, embed_args: ?*[]const TokenWithExpansionLocs, first: TokenWithExpansionLocs) !?[]const u8 {
1366 if (param_toks.len == 0) {
1367 try pp.comp.addDiagnostic(.{
1368 .tag = .expected_filename,
1369 .loc = first.loc,
1370 }, first.expansionSlice());
1371 return null;
1372 }
1373
1374 const char_top = pp.char_buf.items.len;
1375 defer pp.char_buf.items.len = char_top;
1376
1377 // Trim leading/trailing whitespace
1378 var begin: usize = 0;
1379 var end: usize = param_toks.len;
1380 while (begin < end and param_toks[begin].id == .macro_ws) : (begin += 1) {}
1381 while (end > begin and param_toks[end - 1].id == .macro_ws) : (end -= 1) {}
1382 const params = param_toks[begin..end];
1383
1384 if (params.len == 0) {
1385 try pp.comp.addDiagnostic(.{
1386 .tag = .expected_filename,
1387 .loc = first.loc,
1388 }, first.expansionSlice());
1389 return null;
1390 }
1391 // no string pasting
1392 if (embed_args == null and params[0].id == .string_literal and params.len > 1) {
1393 try pp.comp.addDiagnostic(.{
1394 .tag = .closing_paren,
1395 .loc = params[1].loc,
1396 }, params[1].expansionSlice());
1397 return null;
1398 }
1399
1400 for (params, 0..) |tok, i| {
1401 const str = pp.expandedSliceExtra(tok, .preserve_macro_ws);
1402 try pp.char_buf.appendSlice(str);
1403 if (embed_args) |some| {
1404 if ((i == 0 and tok.id == .string_literal) or tok.id == .angle_bracket_right) {
1405 some.* = params[i + 1 ..];
1406 break;
1407 }
1408 }
1409 }
1410
1411 const include_str = pp.char_buf.items[char_top..];
1412 if (include_str.len < 3) {
1413 if (include_str.len == 0) {
1414 try pp.comp.addDiagnostic(.{
1415 .tag = .expected_filename,
1416 .loc = first.loc,
1417 }, first.expansionSlice());
1418 return null;
1419 }
1420 try pp.comp.addDiagnostic(.{
1421 .tag = .empty_filename,
1422 .loc = params[0].loc,
1423 }, params[0].expansionSlice());
1424 return null;
1425 }
1426
1427 switch (include_str[0]) {
1428 '<' => {
1429 if (include_str[include_str.len - 1] != '>') {
1430 // Ugly hack to find out where the '>' should go, since we don't have the closing ')' location
1431 const start = params[0].loc;
1432 try pp.comp.addDiagnostic(.{
1433 .tag = .header_str_closing,
1434 .loc = .{ .id = start.id, .byte_offset = start.byte_offset + @as(u32, @intCast(include_str.len)) + 1, .line = start.line },
1435 }, params[0].expansionSlice());
1436 try pp.comp.addDiagnostic(.{
1437 .tag = .header_str_match,
1438 .loc = params[0].loc,
1439 }, params[0].expansionSlice());
1440 return null;
1441 }
1442 return include_str;
1443 },
1444 '"' => return include_str,
1445 else => {
1446 try pp.comp.addDiagnostic(.{
1447 .tag = .expected_filename,
1448 .loc = params[0].loc,
1449 }, params[0].expansionSlice());
1450 return null;
1451 },
1452 }
1453}
1454
1455fn handleBuiltinMacro(pp: *Preprocessor, builtin: RawToken.Id, param_toks: []const TokenWithExpansionLocs, src_loc: Source.Location) Error!bool {
1456 switch (builtin) {
1457 .macro_param_has_attribute,
1458 .macro_param_has_declspec_attribute,
1459 .macro_param_has_feature,
1460 .macro_param_has_extension,
1461 .macro_param_has_builtin,
1462 => {
1463 var invalid: ?TokenWithExpansionLocs = null;
1464 var identifier: ?TokenWithExpansionLocs = null;
1465 for (param_toks) |tok| {
1466 if (tok.id == .macro_ws) continue;
1467 if (tok.id == .comment) continue;
1468 if (!tok.id.isMacroIdentifier()) {
1469 invalid = tok;
1470 break;
1471 }
1472 if (identifier) |_| invalid = tok else identifier = tok;
1473 }
1474 if (identifier == null and invalid == null) invalid = .{ .id = .eof, .loc = src_loc };
1475 if (invalid) |some| {
1476 try pp.comp.addDiagnostic(
1477 .{ .tag = .feature_check_requires_identifier, .loc = some.loc },
1478 some.expansionSlice(),
1479 );
1480 return false;
1481 }
1482
1483 const ident_str = pp.expandedSlice(identifier.?);
1484 return switch (builtin) {
1485 .macro_param_has_attribute => Attribute.fromString(.gnu, null, ident_str) != null,
1486 .macro_param_has_declspec_attribute => {
1487 return if (pp.comp.langopts.declspec_attrs)
1488 Attribute.fromString(.declspec, null, ident_str) != null
1489 else
1490 false;
1491 },
1492 .macro_param_has_feature => features.hasFeature(pp.comp, ident_str),
1493 .macro_param_has_extension => features.hasExtension(pp.comp, ident_str),
1494 .macro_param_has_builtin => pp.comp.hasBuiltin(ident_str),
1495 else => unreachable,
1496 };
1497 },
1498 .macro_param_has_warning => {
1499 const actual_param = pp.pasteStringsUnsafe(param_toks) catch |er| switch (er) {
1500 error.ExpectedStringLiteral => {
1501 try pp.errStr(param_toks[0], .expected_str_literal_in, "__has_warning");
1502 return false;
1503 },
1504 else => |e| return e,
1505 };
1506 if (!mem.startsWith(u8, actual_param, "-W")) {
1507 try pp.errStr(param_toks[0], .malformed_warning_check, "__has_warning");
1508 return false;
1509 }
1510 const warning_name = actual_param[2..];
1511 return Diagnostics.warningExists(warning_name);
1512 },
1513 .macro_param_is_identifier => {
1514 var invalid: ?TokenWithExpansionLocs = null;
1515 var identifier: ?TokenWithExpansionLocs = null;
1516 for (param_toks) |tok| switch (tok.id) {
1517 .macro_ws => continue,
1518 .comment => continue,
1519 else => {
1520 if (identifier) |_| invalid = tok else identifier = tok;
1521 },
1522 };
1523 if (identifier == null and invalid == null) invalid = .{ .id = .eof, .loc = src_loc };
1524 if (invalid) |some| {
1525 try pp.comp.addDiagnostic(.{
1526 .tag = .missing_tok_builtin,
1527 .loc = some.loc,
1528 .extra = .{ .tok_id_expected = .r_paren },
1529 }, some.expansionSlice());
1530 return false;
1531 }
1532
1533 const id = identifier.?.id;
1534 return id == .identifier or id == .extended_identifier;
1535 },
1536 .macro_param_has_include, .macro_param_has_include_next => {
1537 const include_str = (try pp.reconstructIncludeString(param_toks, null, param_toks[0])) orelse return false;
1538 const include_type: Compilation.IncludeType = switch (include_str[0]) {
1539 '"' => .quotes,
1540 '<' => .angle_brackets,
1541 else => unreachable,
1542 };
1543 const filename = include_str[1 .. include_str.len - 1];
1544 if (builtin == .macro_param_has_include or pp.include_depth == 0) {
1545 if (builtin == .macro_param_has_include_next) {
1546 try pp.comp.addDiagnostic(.{
1547 .tag = .include_next_outside_header,
1548 .loc = src_loc,
1549 }, &.{});
1550 }
1551 return pp.comp.hasInclude(filename, src_loc.id, include_type, .first);
1552 }
1553 return pp.comp.hasInclude(filename, src_loc.id, include_type, .next);
1554 },
1555 else => unreachable,
1556 }
1557}
1558
1559/// Treat whitespace-only paste arguments as empty
1560fn getPasteArgs(args: []const TokenWithExpansionLocs) []const TokenWithExpansionLocs {
1561 for (args) |tok| {
1562 if (tok.id != .macro_ws) return args;
1563 }
1564 return &[1]TokenWithExpansionLocs{.{
1565 .id = .placemarker,
1566 .loc = .{ .id = .generated, .byte_offset = 0, .line = 0 },
1567 }};
1568}
1569
1570fn expandFuncMacro(
1571 pp: *Preprocessor,
1572 macro_tok: TokenWithExpansionLocs,
1573 func_macro: *const Macro,
1574 args: *const MacroArguments,
1575 expanded_args: *const MacroArguments,
1576 hideset_arg: Hideset.Index,
1577) MacroError!ExpandBuf {
1578 var hideset = hideset_arg;
1579 var buf = ExpandBuf.init(pp.gpa);
1580 try buf.ensureTotalCapacity(func_macro.tokens.len);
1581 errdefer buf.deinit();
1582
1583 var expanded_variable_arguments = ExpandBuf.init(pp.gpa);
1584 defer expanded_variable_arguments.deinit();
1585 var variable_arguments = ExpandBuf.init(pp.gpa);
1586 defer variable_arguments.deinit();
1587
1588 if (func_macro.var_args) {
1589 var i: usize = func_macro.params.len;
1590 while (i < expanded_args.items.len) : (i += 1) {
1591 try variable_arguments.appendSlice(args.items[i]);
1592 try expanded_variable_arguments.appendSlice(expanded_args.items[i]);
1593 if (i != expanded_args.items.len - 1) {
1594 const comma = TokenWithExpansionLocs{ .id = .comma, .loc = .{ .id = .generated } };
1595 try variable_arguments.append(comma);
1596 try expanded_variable_arguments.append(comma);
1597 }
1598 }
1599 }
1600
1601 // token concatenation and expansion phase
1602 var tok_i: usize = 0;
1603 while (tok_i < func_macro.tokens.len) : (tok_i += 1) {
1604 const raw = func_macro.tokens[tok_i];
1605 switch (raw.id) {
1606 .hash_hash => while (tok_i + 1 < func_macro.tokens.len) {
1607 const raw_next = func_macro.tokens[tok_i + 1];
1608 tok_i += 1;
1609
1610 var va_opt_buf = ExpandBuf.init(pp.gpa);
1611 defer va_opt_buf.deinit();
1612
1613 const next = switch (raw_next.id) {
1614 .macro_ws => continue,
1615 .hash_hash => continue,
1616 .comment => if (!pp.comp.langopts.preserve_comments_in_macros)
1617 continue
1618 else
1619 &[1]TokenWithExpansionLocs{tokFromRaw(raw_next)},
1620 .macro_param, .macro_param_no_expand => getPasteArgs(args.items[raw_next.end]),
1621 .keyword_va_args => variable_arguments.items,
1622 .keyword_va_opt => blk: {
1623 try pp.expandVaOpt(&va_opt_buf, raw_next, variable_arguments.items.len != 0);
1624 if (va_opt_buf.items.len == 0) break;
1625 break :blk va_opt_buf.items;
1626 },
1627 else => &[1]TokenWithExpansionLocs{tokFromRaw(raw_next)},
1628 };
1629 try pp.pasteTokens(&buf, next);
1630 if (next.len != 0) break;
1631 },
1632 .macro_param_no_expand => {
1633 if (tok_i + 1 < func_macro.tokens.len and func_macro.tokens[tok_i + 1].id == .hash_hash) {
1634 hideset = pp.hideset.get(tokFromRaw(func_macro.tokens[tok_i + 1]).loc);
1635 }
1636 const slice = getPasteArgs(args.items[raw.end]);
1637 const raw_loc = Source.Location{ .id = raw.source, .byte_offset = raw.start, .line = raw.line };
1638 try bufCopyTokens(&buf, slice, &.{raw_loc});
1639 },
1640 .macro_param => {
1641 if (tok_i + 1 < func_macro.tokens.len and func_macro.tokens[tok_i + 1].id == .hash_hash) {
1642 hideset = pp.hideset.get(tokFromRaw(func_macro.tokens[tok_i + 1]).loc);
1643 }
1644 const arg = expanded_args.items[raw.end];
1645 const raw_loc = Source.Location{ .id = raw.source, .byte_offset = raw.start, .line = raw.line };
1646 try bufCopyTokens(&buf, arg, &.{raw_loc});
1647 },
1648 .keyword_va_args => {
1649 const raw_loc = Source.Location{ .id = raw.source, .byte_offset = raw.start, .line = raw.line };
1650 try bufCopyTokens(&buf, expanded_variable_arguments.items, &.{raw_loc});
1651 },
1652 .keyword_va_opt => {
1653 try pp.expandVaOpt(&buf, raw, variable_arguments.items.len != 0);
1654 },
1655 .stringify_param, .stringify_va_args => {
1656 const arg = if (raw.id == .stringify_va_args)
1657 variable_arguments.items
1658 else
1659 args.items[raw.end];
1660
1661 pp.char_buf.clearRetainingCapacity();
1662 try pp.stringify(arg);
1663
1664 const start = pp.comp.generated_buf.items.len;
1665 try pp.comp.generated_buf.appendSlice(pp.gpa, pp.char_buf.items);
1666
1667 try buf.append(try pp.makeGeneratedToken(start, .string_literal, tokFromRaw(raw)));
1668 },
1669 .macro_param_has_attribute,
1670 .macro_param_has_declspec_attribute,
1671 .macro_param_has_warning,
1672 .macro_param_has_feature,
1673 .macro_param_has_extension,
1674 .macro_param_has_builtin,
1675 .macro_param_has_include,
1676 .macro_param_has_include_next,
1677 .macro_param_is_identifier,
1678 => {
1679 const arg = expanded_args.items[0];
1680 const result = if (arg.len == 0) blk: {
1681 const extra = Diagnostics.Message.Extra{ .arguments = .{ .expected = 1, .actual = 0 } };
1682 try pp.comp.addDiagnostic(.{ .tag = .expected_arguments, .loc = macro_tok.loc, .extra = extra }, &.{});
1683 break :blk false;
1684 } else try pp.handleBuiltinMacro(raw.id, arg, macro_tok.loc);
1685 const start = pp.comp.generated_buf.items.len;
1686 const w = pp.comp.generated_buf.writer(pp.gpa);
1687 try w.print("{}\n", .{@intFromBool(result)});
1688 try buf.append(try pp.makeGeneratedToken(start, .pp_num, tokFromRaw(raw)));
1689 },
1690 .macro_param_has_c_attribute => {
1691 const arg = expanded_args.items[0];
1692 const not_found = "0\n";
1693 const result = if (arg.len == 0) blk: {
1694 const extra = Diagnostics.Message.Extra{ .arguments = .{ .expected = 1, .actual = 0 } };
1695 try pp.comp.addDiagnostic(.{ .tag = .expected_arguments, .loc = macro_tok.loc, .extra = extra }, &.{});
1696 break :blk not_found;
1697 } else res: {
1698 var invalid: ?TokenWithExpansionLocs = null;
1699 var vendor_ident: ?TokenWithExpansionLocs = null;
1700 var colon_colon: ?TokenWithExpansionLocs = null;
1701 var attr_ident: ?TokenWithExpansionLocs = null;
1702 for (arg) |tok| {
1703 if (tok.id == .macro_ws) continue;
1704 if (tok.id == .comment) continue;
1705 if (tok.id == .colon_colon) {
1706 if (colon_colon != null or attr_ident == null) {
1707 invalid = tok;
1708 break;
1709 }
1710 vendor_ident = attr_ident;
1711 attr_ident = null;
1712 colon_colon = tok;
1713 continue;
1714 }
1715 if (!tok.id.isMacroIdentifier()) {
1716 invalid = tok;
1717 break;
1718 }
1719 if (attr_ident) |_| {
1720 invalid = tok;
1721 break;
1722 } else attr_ident = tok;
1723 }
1724 if (vendor_ident != null and attr_ident == null) {
1725 invalid = vendor_ident;
1726 } else if (attr_ident == null and invalid == null) {
1727 invalid = .{ .id = .eof, .loc = macro_tok.loc };
1728 }
1729 if (invalid) |some| {
1730 try pp.comp.addDiagnostic(
1731 .{ .tag = .feature_check_requires_identifier, .loc = some.loc },
1732 some.expansionSlice(),
1733 );
1734 break :res not_found;
1735 }
1736 if (vendor_ident) |some| {
1737 const vendor_str = pp.expandedSlice(some);
1738 const attr_str = pp.expandedSlice(attr_ident.?);
1739 const exists = Attribute.fromString(.gnu, vendor_str, attr_str) != null;
1740
1741 const start = pp.comp.generated_buf.items.len;
1742 try pp.comp.generated_buf.appendSlice(pp.gpa, if (exists) "1\n" else "0\n");
1743 try buf.append(try pp.makeGeneratedToken(start, .pp_num, tokFromRaw(raw)));
1744 continue;
1745 }
1746 if (!pp.comp.langopts.standard.atLeast(.c23)) break :res not_found;
1747
1748 const attrs = std.StaticStringMap([]const u8).initComptime(.{
1749 .{ "deprecated", "201904L\n" },
1750 .{ "fallthrough", "201904L\n" },
1751 .{ "maybe_unused", "201904L\n" },
1752 .{ "nodiscard", "202003L\n" },
1753 .{ "noreturn", "202202L\n" },
1754 .{ "_Noreturn", "202202L\n" },
1755 .{ "unsequenced", "202207L\n" },
1756 .{ "reproducible", "202207L\n" },
1757 });
1758
1759 const attr_str = Attribute.normalize(pp.expandedSlice(attr_ident.?));
1760 break :res attrs.get(attr_str) orelse not_found;
1761 };
1762 const start = pp.comp.generated_buf.items.len;
1763 try pp.comp.generated_buf.appendSlice(pp.gpa, result);
1764 try buf.append(try pp.makeGeneratedToken(start, .pp_num, tokFromRaw(raw)));
1765 },
1766 .macro_param_has_embed => {
1767 const arg = expanded_args.items[0];
1768 const not_found = "0\n";
1769 const result = if (arg.len == 0) blk: {
1770 const extra = Diagnostics.Message.Extra{ .arguments = .{ .expected = 1, .actual = 0 } };
1771 try pp.comp.addDiagnostic(.{ .tag = .expected_arguments, .loc = macro_tok.loc, .extra = extra }, &.{});
1772 break :blk not_found;
1773 } else res: {
1774 var embed_args: []const TokenWithExpansionLocs = &.{};
1775 const include_str = (try pp.reconstructIncludeString(arg, &embed_args, arg[0])) orelse
1776 break :res not_found;
1777
1778 var prev = tokFromRaw(raw);
1779 prev.id = .eof;
1780 var it: struct {
1781 i: u32 = 0,
1782 slice: []const TokenWithExpansionLocs,
1783 prev: TokenWithExpansionLocs,
1784 fn next(it: *@This()) TokenWithExpansionLocs {
1785 while (it.i < it.slice.len) switch (it.slice[it.i].id) {
1786 .macro_ws, .whitespace => it.i += 1,
1787 else => break,
1788 } else return it.prev;
1789 defer it.i += 1;
1790 it.prev = it.slice[it.i];
1791 it.prev.id = .eof;
1792 return it.slice[it.i];
1793 }
1794 } = .{ .slice = embed_args, .prev = prev };
1795
1796 while (true) {
1797 const param_first = it.next();
1798 if (param_first.id == .eof) break;
1799 if (param_first.id != .identifier) {
1800 try pp.comp.addDiagnostic(
1801 .{ .tag = .malformed_embed_param, .loc = param_first.loc },
1802 param_first.expansionSlice(),
1803 );
1804 continue;
1805 }
1806
1807 const char_top = pp.char_buf.items.len;
1808 defer pp.char_buf.items.len = char_top;
1809
1810 const maybe_colon = it.next();
1811 const param = switch (maybe_colon.id) {
1812 .colon_colon => blk: {
1813 // vendor::param
1814 const param = it.next();
1815 if (param.id != .identifier) {
1816 try pp.comp.addDiagnostic(
1817 .{ .tag = .malformed_embed_param, .loc = param.loc },
1818 param.expansionSlice(),
1819 );
1820 continue;
1821 }
1822 const l_paren = it.next();
1823 if (l_paren.id != .l_paren) {
1824 try pp.comp.addDiagnostic(
1825 .{ .tag = .malformed_embed_param, .loc = l_paren.loc },
1826 l_paren.expansionSlice(),
1827 );
1828 continue;
1829 }
1830 break :blk "doesn't exist";
1831 },
1832 .l_paren => Attribute.normalize(pp.expandedSlice(param_first)),
1833 else => {
1834 try pp.comp.addDiagnostic(
1835 .{ .tag = .malformed_embed_param, .loc = maybe_colon.loc },
1836 maybe_colon.expansionSlice(),
1837 );
1838 continue;
1839 },
1840 };
1841
1842 var arg_count: u32 = 0;
1843 var first_arg: TokenWithExpansionLocs = undefined;
1844 while (true) {
1845 const next = it.next();
1846 if (next.id == .eof) {
1847 try pp.comp.addDiagnostic(
1848 .{ .tag = .malformed_embed_limit, .loc = param_first.loc },
1849 param_first.expansionSlice(),
1850 );
1851 break;
1852 }
1853 if (next.id == .r_paren) break;
1854 arg_count += 1;
1855 if (arg_count == 1) first_arg = next;
1856 }
1857
1858 if (std.mem.eql(u8, param, "limit")) {
1859 if (arg_count != 1) {
1860 try pp.comp.addDiagnostic(
1861 .{ .tag = .malformed_embed_limit, .loc = param_first.loc },
1862 param_first.expansionSlice(),
1863 );
1864 continue;
1865 }
1866 if (first_arg.id != .pp_num) {
1867 try pp.comp.addDiagnostic(
1868 .{ .tag = .malformed_embed_limit, .loc = param_first.loc },
1869 param_first.expansionSlice(),
1870 );
1871 continue;
1872 }
1873 _ = std.fmt.parseInt(u32, pp.expandedSlice(first_arg), 10) catch {
1874 break :res not_found;
1875 };
1876 } else if (!std.mem.eql(u8, param, "prefix") and !std.mem.eql(u8, param, "suffix") and
1877 !std.mem.eql(u8, param, "if_empty"))
1878 {
1879 break :res not_found;
1880 }
1881 }
1882
1883 const include_type: Compilation.IncludeType = switch (include_str[0]) {
1884 '"' => .quotes,
1885 '<' => .angle_brackets,
1886 else => unreachable,
1887 };
1888 const filename = include_str[1 .. include_str.len - 1];
1889 const contents = (try pp.comp.findEmbed(filename, arg[0].loc.id, include_type, 1)) orelse
1890 break :res not_found;
1891
1892 defer pp.comp.gpa.free(contents);
1893 break :res if (contents.len != 0) "1\n" else "2\n";
1894 };
1895 const start = pp.comp.generated_buf.items.len;
1896 try pp.comp.generated_buf.appendSlice(pp.comp.gpa, result);
1897 try buf.append(try pp.makeGeneratedToken(start, .pp_num, tokFromRaw(raw)));
1898 },
1899 .macro_param_pragma_operator => {
1900 const param_toks = expanded_args.items[0];
1901 // Clang and GCC require exactly one token (so, no parentheses or string pasting)
1902 // even though their error messages indicate otherwise. Ours is slightly more
1903 // descriptive.
1904 var invalid: ?TokenWithExpansionLocs = null;
1905 var string: ?TokenWithExpansionLocs = null;
1906 for (param_toks) |tok| switch (tok.id) {
1907 .string_literal => {
1908 if (string) |_| invalid = tok else string = tok;
1909 },
1910 .macro_ws => continue,
1911 .comment => continue,
1912 else => {
1913 invalid = tok;
1914 break;
1915 },
1916 };
1917 if (string == null and invalid == null) invalid = .{ .loc = macro_tok.loc, .id = .eof };
1918 if (invalid) |some| try pp.comp.addDiagnostic(
1919 .{ .tag = .pragma_operator_string_literal, .loc = some.loc },
1920 some.expansionSlice(),
1921 ) else try pp.pragmaOperator(string.?, macro_tok.loc);
1922 },
1923 .comma => {
1924 if (tok_i + 2 < func_macro.tokens.len and func_macro.tokens[tok_i + 1].id == .hash_hash) {
1925 const hash_hash = func_macro.tokens[tok_i + 1];
1926 var maybe_va_args = func_macro.tokens[tok_i + 2];
1927 var consumed: usize = 2;
1928 if (maybe_va_args.id == .macro_ws and tok_i + 3 < func_macro.tokens.len) {
1929 consumed = 3;
1930 maybe_va_args = func_macro.tokens[tok_i + 3];
1931 }
1932 if (maybe_va_args.id == .keyword_va_args) {
1933 // GNU extension: `, ##__VA_ARGS__` deletes the comma if __VA_ARGS__ is empty
1934 tok_i += consumed;
1935 if (func_macro.params.len == expanded_args.items.len) {
1936 // Empty __VA_ARGS__, drop the comma
1937 try pp.err(hash_hash, .comma_deletion_va_args);
1938 } else if (func_macro.params.len == 0 and expanded_args.items.len == 1 and expanded_args.items[0].len == 0) {
1939 // Ambiguous whether this is "empty __VA_ARGS__" or "__VA_ARGS__ omitted"
1940 if (pp.comp.langopts.standard.isGNU()) {
1941 // GNU standard, drop the comma
1942 try pp.err(hash_hash, .comma_deletion_va_args);
1943 } else {
1944 // C standard, retain the comma
1945 try buf.append(tokFromRaw(raw));
1946 }
1947 } else {
1948 try buf.append(tokFromRaw(raw));
1949 if (expanded_variable_arguments.items.len > 0 or variable_arguments.items.len == func_macro.params.len) {
1950 try pp.err(hash_hash, .comma_deletion_va_args);
1951 }
1952 const raw_loc = Source.Location{
1953 .id = maybe_va_args.source,
1954 .byte_offset = maybe_va_args.start,
1955 .line = maybe_va_args.line,
1956 };
1957 try bufCopyTokens(&buf, expanded_variable_arguments.items, &.{raw_loc});
1958 }
1959 continue;
1960 }
1961 }
1962 // Regular comma, no token pasting with __VA_ARGS__
1963 try buf.append(tokFromRaw(raw));
1964 },
1965 else => try buf.append(tokFromRaw(raw)),
1966 }
1967 }
1968 removePlacemarkers(&buf);
1969
1970 const macro_expansion_locs = macro_tok.expansionSlice();
1971 for (buf.items) |*tok| {
1972 try tok.addExpansionLocation(pp.gpa, &.{macro_tok.loc});
1973 try tok.addExpansionLocation(pp.gpa, macro_expansion_locs);
1974 const tok_hidelist = pp.hideset.get(tok.loc);
1975 const new_hidelist = try pp.hideset.@"union"(tok_hidelist, hideset);
1976 try pp.hideset.put(tok.loc, new_hidelist);
1977 }
1978
1979 return buf;
1980}
1981
1982fn expandVaOpt(
1983 pp: *Preprocessor,
1984 buf: *ExpandBuf,
1985 raw: RawToken,
1986 should_expand: bool,
1987) !void {
1988 if (!should_expand) return;
1989
1990 const source = pp.comp.getSource(raw.source);
1991 var tokenizer: Tokenizer = .{
1992 .buf = source.buf,
1993 .index = raw.start,
1994 .source = raw.source,
1995 .langopts = pp.comp.langopts,
1996 .line = raw.line,
1997 };
1998 while (tokenizer.index < raw.end) {
1999 const tok = tokenizer.next();
2000 try buf.append(tokFromRaw(tok));
2001 }
2002}
2003
2004fn bufCopyTokens(buf: *ExpandBuf, tokens: []const TokenWithExpansionLocs, src: []const Source.Location) !void {
2005 try buf.ensureUnusedCapacity(tokens.len);
2006 for (tokens) |tok| {
2007 var copy = try tok.dupe(buf.allocator);
2008 errdefer TokenWithExpansionLocs.free(copy.expansion_locs, buf.allocator);
2009 try copy.addExpansionLocation(buf.allocator, src);
2010 buf.appendAssumeCapacity(copy);
2011 }
2012}
2013
2014fn nextBufToken(
2015 pp: *Preprocessor,
2016 tokenizer: *Tokenizer,
2017 buf: *ExpandBuf,
2018 start_idx: *usize,
2019 end_idx: *usize,
2020 extend_buf: bool,
2021) Error!TokenWithExpansionLocs {
2022 start_idx.* += 1;
2023 if (start_idx.* == buf.items.len and start_idx.* >= end_idx.*) {
2024 if (extend_buf) {
2025 const raw_tok = tokenizer.next();
2026 if (raw_tok.id.isMacroIdentifier() and
2027 pp.poisoned_identifiers.get(pp.tokSlice(raw_tok)) != null)
2028 try pp.err(raw_tok, .poisoned_identifier);
2029
2030 if (raw_tok.id == .nl) pp.add_expansion_nl += 1;
2031
2032 const new_tok = tokFromRaw(raw_tok);
2033 end_idx.* += 1;
2034 try buf.append(new_tok);
2035 return new_tok;
2036 } else {
2037 return TokenWithExpansionLocs{ .id = .eof, .loc = .{ .id = .generated } };
2038 }
2039 } else {
2040 return buf.items[start_idx.*];
2041 }
2042}
2043
2044fn collectMacroFuncArguments(
2045 pp: *Preprocessor,
2046 tokenizer: *Tokenizer,
2047 buf: *ExpandBuf,
2048 start_idx: *usize,
2049 end_idx: *usize,
2050 extend_buf: bool,
2051 is_builtin: bool,
2052 r_paren: *TokenWithExpansionLocs,
2053) !MacroArguments {
2054 const name_tok = buf.items[start_idx.*];
2055 const saved_tokenizer = tokenizer.*;
2056 const old_end = end_idx.*;
2057
2058 while (true) {
2059 const tok = try nextBufToken(pp, tokenizer, buf, start_idx, end_idx, extend_buf);
2060 switch (tok.id) {
2061 .nl, .whitespace, .macro_ws => {},
2062 .l_paren => break,
2063 else => {
2064 if (is_builtin) {
2065 try pp.errStr(name_tok, .missing_lparen_after_builtin, pp.expandedSlice(name_tok));
2066 }
2067 // Not a macro function call, go over normal identifier, rewind
2068 tokenizer.* = saved_tokenizer;
2069 end_idx.* = old_end;
2070 return error.MissingLParen;
2071 },
2072 }
2073 }
2074
2075 // collect the arguments.
2076 var parens: u32 = 0;
2077 var args = MacroArguments.init(pp.gpa);
2078 errdefer deinitMacroArguments(pp.gpa, &args);
2079 var curArgument = std.ArrayList(TokenWithExpansionLocs).init(pp.gpa);
2080 defer curArgument.deinit();
2081 while (true) {
2082 var tok = try nextBufToken(pp, tokenizer, buf, start_idx, end_idx, extend_buf);
2083 tok.flags.is_macro_arg = true;
2084 switch (tok.id) {
2085 .comma => {
2086 if (parens == 0) {
2087 const owned = try curArgument.toOwnedSlice();
2088 errdefer pp.gpa.free(owned);
2089 try args.append(owned);
2090 } else {
2091 const duped = try tok.dupe(pp.gpa);
2092 errdefer TokenWithExpansionLocs.free(duped.expansion_locs, pp.gpa);
2093 try curArgument.append(duped);
2094 }
2095 },
2096 .l_paren => {
2097 const duped = try tok.dupe(pp.gpa);
2098 errdefer TokenWithExpansionLocs.free(duped.expansion_locs, pp.gpa);
2099 try curArgument.append(duped);
2100 parens += 1;
2101 },
2102 .r_paren => {
2103 if (parens == 0) {
2104 const owned = try curArgument.toOwnedSlice();
2105 errdefer pp.gpa.free(owned);
2106 try args.append(owned);
2107 r_paren.* = tok;
2108 break;
2109 } else {
2110 const duped = try tok.dupe(pp.gpa);
2111 errdefer TokenWithExpansionLocs.free(duped.expansion_locs, pp.gpa);
2112 try curArgument.append(duped);
2113 parens -= 1;
2114 }
2115 },
2116 .eof => {
2117 {
2118 const owned = try curArgument.toOwnedSlice();
2119 errdefer pp.gpa.free(owned);
2120 try args.append(owned);
2121 }
2122 tokenizer.* = saved_tokenizer;
2123 try pp.comp.addDiagnostic(
2124 .{ .tag = .unterminated_macro_arg_list, .loc = name_tok.loc },
2125 name_tok.expansionSlice(),
2126 );
2127 return error.Unterminated;
2128 },
2129 .nl, .whitespace => {
2130 try curArgument.append(.{ .id = .macro_ws, .loc = tok.loc });
2131 },
2132 else => {
2133 const duped = try tok.dupe(pp.gpa);
2134 errdefer TokenWithExpansionLocs.free(duped.expansion_locs, pp.gpa);
2135 try curArgument.append(duped);
2136 },
2137 }
2138 }
2139
2140 return args;
2141}
2142
2143fn removeExpandedTokens(pp: *Preprocessor, buf: *ExpandBuf, start: usize, len: usize, moving_end_idx: *usize) !void {
2144 for (buf.items[start .. start + len]) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2145 try buf.replaceRange(start, len, &.{});
2146 moving_end_idx.* -|= len;
2147}
2148
2149/// The behavior of `defined` depends on whether we are in a preprocessor
2150/// expression context (#if or #elif) or not.
2151/// In a non-expression context it's just an identifier. Within a preprocessor
2152/// expression it is a unary operator or one-argument function.
2153const EvalContext = enum {
2154 expr,
2155 non_expr,
2156};
2157
2158/// Helper for safely iterating over a slice of tokens while skipping whitespace
2159const TokenIterator = struct {
2160 toks: []const TokenWithExpansionLocs,
2161 i: usize,
2162
2163 fn init(toks: []const TokenWithExpansionLocs) TokenIterator {
2164 return .{ .toks = toks, .i = 0 };
2165 }
2166
2167 fn nextNoWS(self: *TokenIterator) ?TokenWithExpansionLocs {
2168 while (self.i < self.toks.len) : (self.i += 1) {
2169 const tok = self.toks[self.i];
2170 if (tok.id == .whitespace or tok.id == .macro_ws) continue;
2171
2172 self.i += 1;
2173 return tok;
2174 }
2175 return null;
2176 }
2177};
2178
2179fn expandMacroExhaustive(
2180 pp: *Preprocessor,
2181 tokenizer: *Tokenizer,
2182 buf: *ExpandBuf,
2183 start_idx: usize,
2184 end_idx: usize,
2185 extend_buf: bool,
2186 eval_ctx: EvalContext,
2187) MacroError!void {
2188 var moving_end_idx = end_idx;
2189 var advance_index: usize = 0;
2190 // rescan loop
2191 var do_rescan = true;
2192 while (do_rescan) {
2193 do_rescan = false;
2194 // expansion loop
2195 var idx: usize = start_idx + advance_index;
2196 while (idx < moving_end_idx) {
2197 const macro_tok = buf.items[idx];
2198 if (macro_tok.id == .keyword_defined and eval_ctx == .expr) {
2199 idx += 1;
2200 var it = TokenIterator.init(buf.items[idx..moving_end_idx]);
2201 if (it.nextNoWS()) |tok| {
2202 switch (tok.id) {
2203 .l_paren => {
2204 _ = it.nextNoWS(); // eat (what should be) identifier
2205 _ = it.nextNoWS(); // eat (what should be) r paren
2206 },
2207 .identifier, .extended_identifier => {},
2208 else => {},
2209 }
2210 }
2211 idx += it.i;
2212 continue;
2213 }
2214 if (!macro_tok.id.isMacroIdentifier() or macro_tok.flags.expansion_disabled) {
2215 idx += 1;
2216 continue;
2217 }
2218 const expanded = pp.expandedSlice(macro_tok);
2219 const macro = pp.defines.getPtr(expanded) orelse {
2220 idx += 1;
2221 continue;
2222 };
2223 const macro_hidelist = pp.hideset.get(macro_tok.loc);
2224 if (pp.hideset.contains(macro_hidelist, expanded)) {
2225 idx += 1;
2226 continue;
2227 }
2228
2229 macro_handler: {
2230 if (macro.is_func) {
2231 var r_paren: TokenWithExpansionLocs = undefined;
2232 var macro_scan_idx = idx;
2233 // to be saved in case this doesn't turn out to be a call
2234 const args = pp.collectMacroFuncArguments(
2235 tokenizer,
2236 buf,
2237 &macro_scan_idx,
2238 &moving_end_idx,
2239 extend_buf,
2240 macro.is_builtin,
2241 &r_paren,
2242 ) catch |er| switch (er) {
2243 error.MissingLParen => {
2244 if (!buf.items[idx].flags.is_macro_arg) buf.items[idx].flags.expansion_disabled = true;
2245 idx += 1;
2246 break :macro_handler;
2247 },
2248 error.Unterminated => {
2249 if (pp.comp.langopts.emulate == .gcc) idx += 1;
2250 try pp.removeExpandedTokens(buf, idx, macro_scan_idx - idx, &moving_end_idx);
2251 break :macro_handler;
2252 },
2253 else => |e| return e,
2254 };
2255 assert(r_paren.id == .r_paren);
2256 var free_arg_expansion_locs = false;
2257 defer {
2258 for (args.items) |item| {
2259 if (free_arg_expansion_locs) for (item) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2260 pp.gpa.free(item);
2261 }
2262 args.deinit();
2263 }
2264 const r_paren_hidelist = pp.hideset.get(r_paren.loc);
2265 var hs = try pp.hideset.intersection(macro_hidelist, r_paren_hidelist);
2266 hs = try pp.hideset.prepend(macro_tok.loc, hs);
2267
2268 var args_count: u32 = @intCast(args.items.len);
2269 // if the macro has zero arguments g() args_count is still 1
2270 // an empty token list g() and a whitespace-only token list g( )
2271 // counts as zero arguments for the purposes of argument-count validation
2272 if (args_count == 1 and macro.params.len == 0) {
2273 for (args.items[0]) |tok| {
2274 if (tok.id != .macro_ws) break;
2275 } else {
2276 args_count = 0;
2277 }
2278 }
2279
2280 // Validate argument count.
2281 const extra = Diagnostics.Message.Extra{
2282 .arguments = .{ .expected = @intCast(macro.params.len), .actual = args_count },
2283 };
2284 if (macro.var_args and args_count < macro.params.len) {
2285 free_arg_expansion_locs = true;
2286 try pp.comp.addDiagnostic(
2287 .{ .tag = .expected_at_least_arguments, .loc = buf.items[idx].loc, .extra = extra },
2288 buf.items[idx].expansionSlice(),
2289 );
2290 idx += 1;
2291 try pp.removeExpandedTokens(buf, idx, macro_scan_idx - idx + 1, &moving_end_idx);
2292 continue;
2293 }
2294 if (!macro.var_args and args_count != macro.params.len) {
2295 free_arg_expansion_locs = true;
2296 try pp.comp.addDiagnostic(
2297 .{ .tag = .expected_arguments, .loc = buf.items[idx].loc, .extra = extra },
2298 buf.items[idx].expansionSlice(),
2299 );
2300 idx += 1;
2301 try pp.removeExpandedTokens(buf, idx, macro_scan_idx - idx + 1, &moving_end_idx);
2302 continue;
2303 }
2304 var expanded_args = MacroArguments.init(pp.gpa);
2305 defer deinitMacroArguments(pp.gpa, &expanded_args);
2306 try expanded_args.ensureTotalCapacity(args.items.len);
2307 for (args.items) |arg| {
2308 var expand_buf = ExpandBuf.init(pp.gpa);
2309 errdefer expand_buf.deinit();
2310 try expand_buf.appendSlice(arg);
2311
2312 try pp.expandMacroExhaustive(tokenizer, &expand_buf, 0, expand_buf.items.len, false, eval_ctx);
2313
2314 expanded_args.appendAssumeCapacity(try expand_buf.toOwnedSlice());
2315 }
2316
2317 var res = try pp.expandFuncMacro(macro_tok, macro, &args, &expanded_args, hs);
2318 defer res.deinit();
2319 const tokens_added = res.items.len;
2320 const tokens_removed = macro_scan_idx - idx + 1;
2321 for (buf.items[idx .. idx + tokens_removed]) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2322 try buf.replaceRange(idx, tokens_removed, res.items);
2323
2324 moving_end_idx += tokens_added;
2325 // Overflow here means that we encountered an unterminated argument list
2326 // while expanding the body of this macro.
2327 moving_end_idx -|= tokens_removed;
2328 idx += tokens_added;
2329 do_rescan = true;
2330 } else {
2331 const res = try pp.expandObjMacro(macro);
2332 defer res.deinit();
2333
2334 const hs = try pp.hideset.prepend(macro_tok.loc, macro_hidelist);
2335
2336 const macro_expansion_locs = macro_tok.expansionSlice();
2337 var increment_idx_by = res.items.len;
2338 for (res.items, 0..) |*tok, i| {
2339 tok.flags.is_macro_arg = macro_tok.flags.is_macro_arg;
2340 try tok.addExpansionLocation(pp.gpa, &.{macro_tok.loc});
2341 try tok.addExpansionLocation(pp.gpa, macro_expansion_locs);
2342
2343 const tok_hidelist = pp.hideset.get(tok.loc);
2344 const new_hidelist = try pp.hideset.@"union"(tok_hidelist, hs);
2345 try pp.hideset.put(tok.loc, new_hidelist);
2346
2347 if (tok.id == .keyword_defined and eval_ctx == .expr) {
2348 try pp.comp.addDiagnostic(.{
2349 .tag = .expansion_to_defined,
2350 .loc = tok.loc,
2351 }, tok.expansionSlice());
2352 }
2353
2354 if (i < increment_idx_by and (tok.id == .keyword_defined or pp.defines.contains(pp.expandedSlice(tok.*)))) {
2355 increment_idx_by = i;
2356 }
2357 }
2358
2359 TokenWithExpansionLocs.free(buf.items[idx].expansion_locs, pp.gpa);
2360 try buf.replaceRange(idx, 1, res.items);
2361 idx += increment_idx_by;
2362 moving_end_idx = moving_end_idx + res.items.len - 1;
2363 do_rescan = true;
2364 }
2365 }
2366 if (idx - start_idx == advance_index + 1 and !do_rescan) {
2367 advance_index += 1;
2368 }
2369 } // end of replacement phase
2370 }
2371 // end of scanning phase
2372
2373 // trim excess buffer
2374 for (buf.items[moving_end_idx..]) |item| {
2375 TokenWithExpansionLocs.free(item.expansion_locs, pp.gpa);
2376 }
2377 buf.items.len = moving_end_idx;
2378}
2379
2380/// Try to expand a macro after a possible candidate has been read from the `tokenizer`
2381/// into the `raw` token passed as argument
2382fn expandMacro(pp: *Preprocessor, tokenizer: *Tokenizer, raw: RawToken) MacroError!void {
2383 var source_tok = tokFromRaw(raw);
2384 if (!raw.id.isMacroIdentifier()) {
2385 source_tok.id.simplifyMacroKeyword();
2386 return pp.addToken(source_tok);
2387 }
2388 pp.top_expansion_buf.items.len = 0;
2389 try pp.top_expansion_buf.append(source_tok);
2390 pp.expansion_source_loc = source_tok.loc;
2391
2392 pp.hideset.clearRetainingCapacity();
2393 try pp.expandMacroExhaustive(tokenizer, &pp.top_expansion_buf, 0, 1, true, .non_expr);
2394 try pp.ensureUnusedTokenCapacity(pp.top_expansion_buf.items.len);
2395 for (pp.top_expansion_buf.items) |*tok| {
2396 if (tok.id == .macro_ws and !pp.preserve_whitespace) {
2397 TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2398 continue;
2399 }
2400 if (tok.id == .comment and !pp.comp.langopts.preserve_comments_in_macros) {
2401 TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2402 continue;
2403 }
2404 if (tok.id == .placemarker) {
2405 TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
2406 continue;
2407 }
2408 tok.id.simplifyMacroKeywordExtra(true);
2409 pp.addTokenAssumeCapacity(tok.*);
2410 }
2411 if (pp.preserve_whitespace) {
2412 try pp.ensureUnusedTokenCapacity(pp.add_expansion_nl);
2413 while (pp.add_expansion_nl > 0) : (pp.add_expansion_nl -= 1) {
2414 pp.addTokenAssumeCapacity(.{ .id = .nl, .loc = .{
2415 .id = tokenizer.source,
2416 .line = tokenizer.line,
2417 } });
2418 }
2419 }
2420}
2421
2422fn expandedSliceExtra(pp: *const Preprocessor, tok: anytype, macro_ws_handling: enum { single_macro_ws, preserve_macro_ws }) []const u8 {
2423 if (tok.id.lexeme()) |some| {
2424 if (!tok.id.allowsDigraphs(pp.comp.langopts) and !(tok.id == .macro_ws and macro_ws_handling == .preserve_macro_ws)) return some;
2425 }
2426 var tmp_tokenizer = Tokenizer{
2427 .buf = pp.comp.getSource(tok.loc.id).buf,
2428 .langopts = pp.comp.langopts,
2429 .index = tok.loc.byte_offset,
2430 .source = .generated,
2431 };
2432 if (tok.id == .macro_string) {
2433 while (true) : (tmp_tokenizer.index += 1) {
2434 if (tmp_tokenizer.buf[tmp_tokenizer.index] == '>') break;
2435 }
2436 return tmp_tokenizer.buf[tok.loc.byte_offset .. tmp_tokenizer.index + 1];
2437 }
2438 const res = tmp_tokenizer.next();
2439 return tmp_tokenizer.buf[res.start..res.end];
2440}
2441
2442/// Get expanded token source string.
2443pub fn expandedSlice(pp: *const Preprocessor, tok: anytype) []const u8 {
2444 return pp.expandedSliceExtra(tok, .single_macro_ws);
2445}
2446
2447/// Concat two tokens and add the result to pp.generated
2448fn pasteTokens(pp: *Preprocessor, lhs_toks: *ExpandBuf, rhs_toks: []const TokenWithExpansionLocs) Error!void {
2449 const lhs = while (lhs_toks.popOrNull()) |lhs| {
2450 if ((pp.comp.langopts.preserve_comments_in_macros and lhs.id == .comment) or
2451 (lhs.id != .macro_ws and lhs.id != .comment))
2452 break lhs;
2453
2454 TokenWithExpansionLocs.free(lhs.expansion_locs, pp.gpa);
2455 } else {
2456 return bufCopyTokens(lhs_toks, rhs_toks, &.{});
2457 };
2458
2459 var rhs_rest: u32 = 1;
2460 const rhs = for (rhs_toks) |rhs| {
2461 if ((pp.comp.langopts.preserve_comments_in_macros and rhs.id == .comment) or
2462 (rhs.id != .macro_ws and rhs.id != .comment))
2463 break rhs;
2464
2465 rhs_rest += 1;
2466 } else {
2467 return lhs_toks.appendAssumeCapacity(lhs);
2468 };
2469 defer TokenWithExpansionLocs.free(lhs.expansion_locs, pp.gpa);
2470
2471 const start = pp.comp.generated_buf.items.len;
2472 const end = start + pp.expandedSlice(lhs).len + pp.expandedSlice(rhs).len;
2473 try pp.comp.generated_buf.ensureTotalCapacity(pp.gpa, end + 1); // +1 for a newline
2474 // We cannot use the same slices here since they might be invalidated by `ensureCapacity`
2475 pp.comp.generated_buf.appendSliceAssumeCapacity(pp.expandedSlice(lhs));
2476 pp.comp.generated_buf.appendSliceAssumeCapacity(pp.expandedSlice(rhs));
2477 pp.comp.generated_buf.appendAssumeCapacity('\n');
2478
2479 // Try to tokenize the result.
2480 var tmp_tokenizer = Tokenizer{
2481 .buf = pp.comp.generated_buf.items,
2482 .langopts = pp.comp.langopts,
2483 .index = @intCast(start),
2484 .source = .generated,
2485 };
2486 const pasted_token = tmp_tokenizer.nextNoWSComments();
2487 const next = tmp_tokenizer.nextNoWSComments();
2488 const pasted_id = if (lhs.id == .placemarker and rhs.id == .placemarker)
2489 .placemarker
2490 else
2491 pasted_token.id;
2492 try lhs_toks.append(try pp.makeGeneratedToken(start, pasted_id, lhs));
2493
2494 if (next.id != .nl and next.id != .eof) {
2495 try pp.errStr(
2496 lhs,
2497 .pasting_formed_invalid,
2498 try pp.comp.diagnostics.arena.allocator().dupe(u8, pp.comp.generated_buf.items[start..end]),
2499 );
2500 try lhs_toks.append(tokFromRaw(next));
2501 }
2502
2503 try bufCopyTokens(lhs_toks, rhs_toks[rhs_rest..], &.{});
2504}
2505
2506fn makeGeneratedToken(pp: *Preprocessor, start: usize, id: Token.Id, source: TokenWithExpansionLocs) !TokenWithExpansionLocs {
2507 var pasted_token = TokenWithExpansionLocs{ .id = id, .loc = .{
2508 .id = .generated,
2509 .byte_offset = @intCast(start),
2510 .line = pp.generated_line,
2511 } };
2512 pp.generated_line += 1;
2513 try pasted_token.addExpansionLocation(pp.gpa, &.{source.loc});
2514 try pasted_token.addExpansionLocation(pp.gpa, source.expansionSlice());
2515 return pasted_token;
2516}
2517
2518/// Defines a new macro and warns if it is a duplicate
2519fn defineMacro(pp: *Preprocessor, define_tok: RawToken, name_tok: RawToken, macro: Macro) Error!void {
2520 const name_str = pp.tokSlice(name_tok);
2521 const gop = try pp.defines.getOrPut(pp.gpa, name_str);
2522 if (gop.found_existing and !gop.value_ptr.eql(macro, pp)) {
2523 const tag: Diagnostics.Tag = if (gop.value_ptr.is_builtin) .builtin_macro_redefined else .macro_redefined;
2524 const start = pp.comp.diagnostics.list.items.len;
2525 try pp.comp.addDiagnostic(.{
2526 .tag = tag,
2527 .loc = .{ .id = name_tok.source, .byte_offset = name_tok.start, .line = name_tok.line },
2528 .extra = .{ .str = name_str },
2529 }, &.{});
2530 if (!gop.value_ptr.is_builtin and pp.comp.diagnostics.list.items.len != start) {
2531 try pp.comp.addDiagnostic(.{
2532 .tag = .previous_definition,
2533 .loc = gop.value_ptr.loc,
2534 }, &.{});
2535 }
2536 }
2537 if (pp.verbose) {
2538 pp.verboseLog(name_tok, "macro {s} defined", .{name_str});
2539 }
2540 if (pp.store_macro_tokens) {
2541 try pp.addToken(tokFromRaw(define_tok));
2542 }
2543 gop.value_ptr.* = macro;
2544}
2545
2546/// Handle a #define directive.
2547fn define(pp: *Preprocessor, tokenizer: *Tokenizer, define_tok: RawToken) Error!void {
2548 // Get macro name and validate it.
2549 const macro_name = tokenizer.nextNoWS();
2550 if (macro_name.id == .keyword_defined) {
2551 try pp.err(macro_name, .defined_as_macro_name);
2552 return skipToNl(tokenizer);
2553 }
2554 if (!macro_name.id.isMacroIdentifier()) {
2555 try pp.err(macro_name, .macro_name_must_be_identifier);
2556 return skipToNl(tokenizer);
2557 }
2558 var macro_name_token_id = macro_name.id;
2559 macro_name_token_id.simplifyMacroKeyword();
2560 switch (macro_name_token_id) {
2561 .identifier, .extended_identifier => {},
2562 else => if (macro_name_token_id.isMacroIdentifier()) {
2563 try pp.err(macro_name, .keyword_macro);
2564 },
2565 }
2566
2567 // Check for function macros and empty defines.
2568 var first = tokenizer.next();
2569 switch (first.id) {
2570 .nl, .eof => return pp.defineMacro(define_tok, macro_name, .{
2571 .params = &.{},
2572 .tokens = &.{},
2573 .var_args = false,
2574 .loc = tokFromRaw(macro_name).loc,
2575 .is_func = false,
2576 }),
2577 .whitespace => first = tokenizer.next(),
2578 .l_paren => return pp.defineFn(tokenizer, define_tok, macro_name, first),
2579 else => try pp.err(first, .whitespace_after_macro_name),
2580 }
2581 if (first.id == .hash_hash) {
2582 try pp.err(first, .hash_hash_at_start);
2583 return skipToNl(tokenizer);
2584 }
2585 first.id.simplifyMacroKeyword();
2586
2587 pp.token_buf.items.len = 0; // Safe to use since we can only be in one directive at a time.
2588
2589 var need_ws = false;
2590 // Collect the token body and validate any ## found.
2591 var tok = first;
2592 while (true) {
2593 tok.id.simplifyMacroKeyword();
2594 switch (tok.id) {
2595 .hash_hash => {
2596 const next = tokenizer.nextNoWSComments();
2597 switch (next.id) {
2598 .nl, .eof => {
2599 try pp.err(tok, .hash_hash_at_end);
2600 return;
2601 },
2602 .hash_hash => {
2603 try pp.err(next, .hash_hash_at_end);
2604 return;
2605 },
2606 else => {},
2607 }
2608 try pp.token_buf.append(tok);
2609 try pp.token_buf.append(next);
2610 },
2611 .nl, .eof => break,
2612 .comment => if (pp.comp.langopts.preserve_comments_in_macros) {
2613 if (need_ws) {
2614 need_ws = false;
2615 try pp.token_buf.append(.{ .id = .macro_ws, .source = .generated });
2616 }
2617 try pp.token_buf.append(tok);
2618 },
2619 .whitespace => need_ws = true,
2620 .unterminated_string_literal, .unterminated_char_literal, .empty_char_literal => |tag| {
2621 try pp.err(tok, invalidTokenDiagnostic(tag));
2622 try pp.token_buf.append(tok);
2623 },
2624 .unterminated_comment => try pp.err(tok, .unterminated_comment),
2625 else => {
2626 if (tok.id != .whitespace and need_ws) {
2627 need_ws = false;
2628 try pp.token_buf.append(.{ .id = .macro_ws, .source = .generated });
2629 }
2630 try pp.token_buf.append(tok);
2631 },
2632 }
2633 tok = tokenizer.next();
2634 }
2635
2636 const list = try pp.arena.allocator().dupe(RawToken, pp.token_buf.items);
2637 try pp.defineMacro(define_tok, macro_name, .{
2638 .loc = tokFromRaw(macro_name).loc,
2639 .tokens = list,
2640 .params = undefined,
2641 .is_func = false,
2642 .var_args = false,
2643 });
2644}
2645
2646/// Handle a function like #define directive.
2647fn defineFn(pp: *Preprocessor, tokenizer: *Tokenizer, define_tok: RawToken, macro_name: RawToken, l_paren: RawToken) Error!void {
2648 assert(macro_name.id.isMacroIdentifier());
2649 var params = std.ArrayList([]const u8).init(pp.gpa);
2650 defer params.deinit();
2651
2652 // Parse the parameter list.
2653 var gnu_var_args: []const u8 = "";
2654 var var_args = false;
2655 while (true) {
2656 var tok = tokenizer.nextNoWS();
2657 if (tok.id == .r_paren) break;
2658 if (tok.id == .eof) return pp.err(tok, .unterminated_macro_param_list);
2659 if (tok.id == .ellipsis) {
2660 var_args = true;
2661 const r_paren = tokenizer.nextNoWS();
2662 if (r_paren.id != .r_paren) {
2663 try pp.err(r_paren, .missing_paren_param_list);
2664 try pp.err(l_paren, .to_match_paren);
2665 return skipToNl(tokenizer);
2666 }
2667 break;
2668 }
2669 if (!tok.id.isMacroIdentifier()) {
2670 try pp.err(tok, .invalid_token_param_list);
2671 return skipToNl(tokenizer);
2672 }
2673
2674 try params.append(pp.tokSlice(tok));
2675
2676 tok = tokenizer.nextNoWS();
2677 if (tok.id == .ellipsis) {
2678 try pp.err(tok, .gnu_va_macro);
2679 gnu_var_args = params.pop();
2680 const r_paren = tokenizer.nextNoWS();
2681 if (r_paren.id != .r_paren) {
2682 try pp.err(r_paren, .missing_paren_param_list);
2683 try pp.err(l_paren, .to_match_paren);
2684 return skipToNl(tokenizer);
2685 }
2686 break;
2687 } else if (tok.id == .r_paren) {
2688 break;
2689 } else if (tok.id != .comma) {
2690 try pp.err(tok, .expected_comma_param_list);
2691 return skipToNl(tokenizer);
2692 }
2693 }
2694
2695 var need_ws = false;
2696 // Collect the body tokens and validate # and ##'s found.
2697 pp.token_buf.items.len = 0; // Safe to use since we can only be in one directive at a time.
2698 tok_loop: while (true) {
2699 var tok = tokenizer.next();
2700 switch (tok.id) {
2701 .nl, .eof => break,
2702 .whitespace => need_ws = pp.token_buf.items.len != 0,
2703 .comment => if (!pp.comp.langopts.preserve_comments_in_macros) continue else {
2704 if (need_ws) {
2705 need_ws = false;
2706 try pp.token_buf.append(.{ .id = .macro_ws, .source = .generated });
2707 }
2708 try pp.token_buf.append(tok);
2709 },
2710 .hash => {
2711 if (tok.id != .whitespace and need_ws) {
2712 need_ws = false;
2713 try pp.token_buf.append(.{ .id = .macro_ws, .source = .generated });
2714 }
2715 const param = tokenizer.nextNoWS();
2716 blk: {
2717 if (var_args and param.id == .keyword_va_args) {
2718 tok.id = .stringify_va_args;
2719 try pp.token_buf.append(tok);
2720 continue :tok_loop;
2721 }
2722 if (!param.id.isMacroIdentifier()) break :blk;
2723 const s = pp.tokSlice(param);
2724 if (mem.eql(u8, s, gnu_var_args)) {
2725 tok.id = .stringify_va_args;
2726 try pp.token_buf.append(tok);
2727 continue :tok_loop;
2728 }
2729 for (params.items, 0..) |p, i| {
2730 if (mem.eql(u8, p, s)) {
2731 tok.id = .stringify_param;
2732 tok.end = @intCast(i);
2733 try pp.token_buf.append(tok);
2734 continue :tok_loop;
2735 }
2736 }
2737 }
2738 try pp.err(param, .hash_not_followed_param);
2739 return skipToNl(tokenizer);
2740 },
2741 .hash_hash => {
2742 need_ws = false;
2743 // if ## appears at the beginning, the token buf is still empty
2744 // in this case, error out
2745 if (pp.token_buf.items.len == 0) {
2746 try pp.err(tok, .hash_hash_at_start);
2747 return skipToNl(tokenizer);
2748 }
2749 const saved_tokenizer = tokenizer.*;
2750 const next = tokenizer.nextNoWSComments();
2751 if (next.id == .nl or next.id == .eof) {
2752 try pp.err(tok, .hash_hash_at_end);
2753 return;
2754 }
2755 tokenizer.* = saved_tokenizer;
2756 // convert the previous token to .macro_param_no_expand if it was .macro_param
2757 if (pp.token_buf.items[pp.token_buf.items.len - 1].id == .macro_param) {
2758 pp.token_buf.items[pp.token_buf.items.len - 1].id = .macro_param_no_expand;
2759 }
2760 try pp.token_buf.append(tok);
2761 },
2762 .unterminated_string_literal, .unterminated_char_literal, .empty_char_literal => |tag| {
2763 try pp.err(tok, invalidTokenDiagnostic(tag));
2764 try pp.token_buf.append(tok);
2765 },
2766 .unterminated_comment => try pp.err(tok, .unterminated_comment),
2767 else => {
2768 if (tok.id != .whitespace and need_ws) {
2769 need_ws = false;
2770 try pp.token_buf.append(.{ .id = .macro_ws, .source = .generated });
2771 }
2772 if (var_args and tok.id == .keyword_va_args) {
2773 // do nothing
2774 } else if (var_args and tok.id == .keyword_va_opt) {
2775 const opt_l_paren = tokenizer.next();
2776 if (opt_l_paren.id != .l_paren) {
2777 try pp.err(opt_l_paren, .va_opt_lparen);
2778 return skipToNl(tokenizer);
2779 }
2780 tok.start = opt_l_paren.end;
2781
2782 var parens: u32 = 0;
2783 while (true) {
2784 const opt_tok = tokenizer.next();
2785 switch (opt_tok.id) {
2786 .l_paren => parens += 1,
2787 .r_paren => if (parens == 0) {
2788 break;
2789 } else {
2790 parens -= 1;
2791 },
2792 .nl, .eof => {
2793 try pp.err(opt_tok, .va_opt_rparen);
2794 try pp.err(opt_l_paren, .to_match_paren);
2795 return skipToNl(tokenizer);
2796 },
2797 .whitespace => {},
2798 else => tok.end = opt_tok.end,
2799 }
2800 }
2801 } else if (tok.id.isMacroIdentifier()) {
2802 tok.id.simplifyMacroKeyword();
2803 const s = pp.tokSlice(tok);
2804 if (mem.eql(u8, gnu_var_args, s)) {
2805 tok.id = .keyword_va_args;
2806 } else for (params.items, 0..) |param, i| {
2807 if (mem.eql(u8, param, s)) {
2808 // NOTE: it doesn't matter to assign .macro_param_no_expand
2809 // here in case a ## was the previous token, because
2810 // ## processing will eat this token with the same semantics
2811 tok.id = .macro_param;
2812 tok.end = @intCast(i);
2813 break;
2814 }
2815 }
2816 }
2817 try pp.token_buf.append(tok);
2818 },
2819 }
2820 }
2821
2822 const param_list = try pp.arena.allocator().dupe([]const u8, params.items);
2823 const token_list = try pp.arena.allocator().dupe(RawToken, pp.token_buf.items);
2824 try pp.defineMacro(define_tok, macro_name, .{
2825 .is_func = true,
2826 .params = param_list,
2827 .var_args = var_args or gnu_var_args.len != 0,
2828 .tokens = token_list,
2829 .loc = tokFromRaw(macro_name).loc,
2830 });
2831}
2832
2833/// Handle an #embed directive
2834/// embedDirective : ("FILENAME" | <FILENAME>) embedParam*
2835/// embedParam : IDENTIFIER (:: IDENTIFIER)? '(' <tokens> ')'
2836fn embed(pp: *Preprocessor, tokenizer: *Tokenizer) MacroError!void {
2837 const first = tokenizer.nextNoWS();
2838 const filename_tok = pp.findIncludeFilenameToken(first, tokenizer, .ignore_trailing_tokens) catch |er| switch (er) {
2839 error.InvalidInclude => return,
2840 else => |e| return e,
2841 };
2842 defer TokenWithExpansionLocs.free(filename_tok.expansion_locs, pp.gpa);
2843
2844 // Check for empty filename.
2845 const tok_slice = pp.expandedSliceExtra(filename_tok, .single_macro_ws);
2846 if (tok_slice.len < 3) {
2847 try pp.err(first, .empty_filename);
2848 return;
2849 }
2850 const filename = tok_slice[1 .. tok_slice.len - 1];
2851 const include_type: Compilation.IncludeType = switch (filename_tok.id) {
2852 .string_literal => .quotes,
2853 .macro_string => .angle_brackets,
2854 else => unreachable,
2855 };
2856
2857 // Index into `token_buf`
2858 const Range = struct {
2859 start: u32,
2860 end: u32,
2861
2862 fn expand(opt_range: ?@This(), pp_: *Preprocessor, tokenizer_: *Tokenizer) !void {
2863 const range = opt_range orelse return;
2864 const slice = pp_.token_buf.items[range.start..range.end];
2865 for (slice) |tok| {
2866 try pp_.expandMacro(tokenizer_, tok);
2867 }
2868 }
2869 };
2870 pp.token_buf.items.len = 0;
2871
2872 var limit: ?u32 = null;
2873 var prefix: ?Range = null;
2874 var suffix: ?Range = null;
2875 var if_empty: ?Range = null;
2876 while (true) {
2877 const param_first = tokenizer.nextNoWS();
2878 switch (param_first.id) {
2879 .nl, .eof => break,
2880 .identifier => {},
2881 else => {
2882 try pp.err(param_first, .malformed_embed_param);
2883 continue;
2884 },
2885 }
2886
2887 const char_top = pp.char_buf.items.len;
2888 defer pp.char_buf.items.len = char_top;
2889
2890 const maybe_colon = tokenizer.colonColon();
2891 const param = switch (maybe_colon.id) {
2892 .colon_colon => blk: {
2893 // vendor::param
2894 const param = tokenizer.nextNoWS();
2895 if (param.id != .identifier) {
2896 try pp.err(param, .malformed_embed_param);
2897 continue;
2898 }
2899 const l_paren = tokenizer.nextNoWS();
2900 if (l_paren.id != .l_paren) {
2901 try pp.err(l_paren, .malformed_embed_param);
2902 continue;
2903 }
2904 try pp.char_buf.appendSlice(Attribute.normalize(pp.tokSlice(param_first)));
2905 try pp.char_buf.appendSlice("::");
2906 try pp.char_buf.appendSlice(Attribute.normalize(pp.tokSlice(param)));
2907 break :blk pp.char_buf.items;
2908 },
2909 .l_paren => Attribute.normalize(pp.tokSlice(param_first)),
2910 else => {
2911 try pp.err(maybe_colon, .malformed_embed_param);
2912 continue;
2913 },
2914 };
2915
2916 const start: u32 = @intCast(pp.token_buf.items.len);
2917 while (true) {
2918 const next = tokenizer.nextNoWS();
2919 if (next.id == .r_paren) break;
2920 if (next.id == .eof) {
2921 try pp.err(maybe_colon, .malformed_embed_param);
2922 break;
2923 }
2924 try pp.token_buf.append(next);
2925 }
2926 const end: u32 = @intCast(pp.token_buf.items.len);
2927
2928 if (std.mem.eql(u8, param, "limit")) {
2929 if (limit != null) {
2930 try pp.errStr(tokFromRaw(param_first), .duplicate_embed_param, "limit");
2931 continue;
2932 }
2933 if (start + 1 != end) {
2934 try pp.err(param_first, .malformed_embed_limit);
2935 continue;
2936 }
2937 const limit_tok = pp.token_buf.items[start];
2938 if (limit_tok.id != .pp_num) {
2939 try pp.err(param_first, .malformed_embed_limit);
2940 continue;
2941 }
2942 limit = std.fmt.parseInt(u32, pp.tokSlice(limit_tok), 10) catch {
2943 try pp.err(limit_tok, .malformed_embed_limit);
2944 continue;
2945 };
2946 pp.token_buf.items.len = start;
2947 } else if (std.mem.eql(u8, param, "prefix")) {
2948 if (prefix != null) {
2949 try pp.errStr(tokFromRaw(param_first), .duplicate_embed_param, "prefix");
2950 continue;
2951 }
2952 prefix = .{ .start = start, .end = end };
2953 } else if (std.mem.eql(u8, param, "suffix")) {
2954 if (suffix != null) {
2955 try pp.errStr(tokFromRaw(param_first), .duplicate_embed_param, "suffix");
2956 continue;
2957 }
2958 suffix = .{ .start = start, .end = end };
2959 } else if (std.mem.eql(u8, param, "if_empty")) {
2960 if (if_empty != null) {
2961 try pp.errStr(tokFromRaw(param_first), .duplicate_embed_param, "if_empty");
2962 continue;
2963 }
2964 if_empty = .{ .start = start, .end = end };
2965 } else {
2966 try pp.errStr(
2967 tokFromRaw(param_first),
2968 .unsupported_embed_param,
2969 try pp.comp.diagnostics.arena.allocator().dupe(u8, param),
2970 );
2971 pp.token_buf.items.len = start;
2972 }
2973 }
2974
2975 const embed_bytes = (try pp.comp.findEmbed(filename, first.source, include_type, limit)) orelse
2976 return pp.fatalNotFound(filename_tok, filename);
2977 defer pp.comp.gpa.free(embed_bytes);
2978
2979 try Range.expand(prefix, pp, tokenizer);
2980
2981 if (embed_bytes.len == 0) {
2982 try Range.expand(if_empty, pp, tokenizer);
2983 try Range.expand(suffix, pp, tokenizer);
2984 return;
2985 }
2986
2987 try pp.ensureUnusedTokenCapacity(2 * embed_bytes.len - 1); // N bytes and N-1 commas
2988
2989 // TODO: We currently only support systems with CHAR_BIT == 8
2990 // If the target's CHAR_BIT is not 8, we need to write out correctly-sized embed_bytes
2991 // and correctly account for the target's endianness
2992 const writer = pp.comp.generated_buf.writer(pp.gpa);
2993
2994 {
2995 const byte = embed_bytes[0];
2996 const start = pp.comp.generated_buf.items.len;
2997 try writer.print("{d}", .{byte});
2998 pp.addTokenAssumeCapacity(try pp.makeGeneratedToken(start, .embed_byte, filename_tok));
2999 }
3000
3001 for (embed_bytes[1..]) |byte| {
3002 const start = pp.comp.generated_buf.items.len;
3003 try writer.print(",{d}", .{byte});
3004 pp.addTokenAssumeCapacity(.{ .id = .comma, .loc = .{ .id = .generated, .byte_offset = @intCast(start) } });
3005 pp.addTokenAssumeCapacity(try pp.makeGeneratedToken(start + 1, .embed_byte, filename_tok));
3006 }
3007 try pp.comp.generated_buf.append(pp.gpa, '\n');
3008
3009 try Range.expand(suffix, pp, tokenizer);
3010}
3011
3012// Handle a #include directive.
3013fn include(pp: *Preprocessor, tokenizer: *Tokenizer, which: Compilation.WhichInclude) MacroError!void {
3014 const first = tokenizer.nextNoWS();
3015 const new_source = findIncludeSource(pp, tokenizer, first, which) catch |er| switch (er) {
3016 error.InvalidInclude => return,
3017 else => |e| return e,
3018 };
3019
3020 // Prevent stack overflow
3021 pp.include_depth += 1;
3022 defer pp.include_depth -= 1;
3023 if (pp.include_depth > max_include_depth) {
3024 try pp.comp.addDiagnostic(.{
3025 .tag = .too_many_includes,
3026 .loc = .{ .id = first.source, .byte_offset = first.start, .line = first.line },
3027 }, &.{});
3028 return error.StopPreprocessing;
3029 }
3030
3031 if (pp.include_guards.get(new_source.id)) |guard| {
3032 if (pp.defines.contains(guard)) return;
3033 }
3034
3035 if (pp.verbose) {
3036 pp.verboseLog(first, "include file {s}", .{new_source.path});
3037 }
3038
3039 const token_state = pp.getTokenState();
3040 try pp.addIncludeStart(new_source);
3041 const eof = pp.preprocessExtra(new_source) catch |er| switch (er) {
3042 error.StopPreprocessing => {
3043 for (pp.expansion_entries.items(.locs)[token_state.expansion_entries_len..]) |loc| TokenWithExpansionLocs.free(loc, pp.gpa);
3044 pp.restoreTokenState(token_state);
3045 return;
3046 },
3047 else => |e| return e,
3048 };
3049 try eof.checkMsEof(new_source, pp.comp);
3050 if (pp.preserve_whitespace and pp.tokens.items(.id)[pp.tokens.len - 1] != .nl) {
3051 try pp.addToken(.{ .id = .nl, .loc = .{
3052 .id = tokenizer.source,
3053 .line = tokenizer.line,
3054 } });
3055 }
3056 if (pp.linemarkers == .none) return;
3057 var next = first;
3058 while (true) {
3059 var tmp = tokenizer.*;
3060 next = tmp.nextNoWS();
3061 if (next.id != .nl) break;
3062 tokenizer.* = tmp;
3063 }
3064 try pp.addIncludeResume(next.source, next.end, next.line);
3065}
3066
3067/// tokens that are part of a pragma directive can happen in 3 ways:
3068/// 1. directly in the text via `#pragma ...`
3069/// 2. Via a string literal argument to `_Pragma`
3070/// 3. Via a stringified macro argument which is used as an argument to `_Pragma`
3071/// operator_loc: Location of `_Pragma`; null if this is from #pragma
3072/// arg_locs: expansion locations of the argument to _Pragma. empty if #pragma or a raw string literal was used
3073fn makePragmaToken(pp: *Preprocessor, raw: RawToken, operator_loc: ?Source.Location, arg_locs: []const Source.Location) !TokenWithExpansionLocs {
3074 var tok = tokFromRaw(raw);
3075 if (operator_loc) |loc| {
3076 try tok.addExpansionLocation(pp.gpa, &.{loc});
3077 }
3078 try tok.addExpansionLocation(pp.gpa, arg_locs);
3079 return tok;
3080}
3081
3082pub fn addToken(pp: *Preprocessor, tok: TokenWithExpansionLocs) !void {
3083 if (tok.expansion_locs) |expansion_locs| {
3084 try pp.expansion_entries.append(pp.gpa, .{ .idx = @intCast(pp.tokens.len), .locs = expansion_locs });
3085 }
3086 try pp.tokens.append(pp.gpa, .{ .id = tok.id, .loc = tok.loc });
3087}
3088
3089pub fn addTokenAssumeCapacity(pp: *Preprocessor, tok: TokenWithExpansionLocs) void {
3090 if (tok.expansion_locs) |expansion_locs| {
3091 pp.expansion_entries.appendAssumeCapacity(.{ .idx = @intCast(pp.tokens.len), .locs = expansion_locs });
3092 }
3093 pp.tokens.appendAssumeCapacity(.{ .id = tok.id, .loc = tok.loc });
3094}
3095
3096pub fn ensureTotalTokenCapacity(pp: *Preprocessor, capacity: usize) !void {
3097 try pp.tokens.ensureTotalCapacity(pp.gpa, capacity);
3098 try pp.expansion_entries.ensureTotalCapacity(pp.gpa, capacity);
3099}
3100
3101pub fn ensureUnusedTokenCapacity(pp: *Preprocessor, capacity: usize) !void {
3102 try pp.tokens.ensureUnusedCapacity(pp.gpa, capacity);
3103 try pp.expansion_entries.ensureUnusedCapacity(pp.gpa, capacity);
3104}
3105
3106/// Handle a pragma directive
3107fn pragma(pp: *Preprocessor, tokenizer: *Tokenizer, pragma_tok: RawToken, operator_loc: ?Source.Location, arg_locs: []const Source.Location) !void {
3108 const name_tok = tokenizer.nextNoWS();
3109 if (name_tok.id == .nl or name_tok.id == .eof) return;
3110
3111 const name = pp.tokSlice(name_tok);
3112 try pp.addToken(try pp.makePragmaToken(pragma_tok, operator_loc, arg_locs));
3113 const pragma_start: u32 = @intCast(pp.tokens.len);
3114
3115 const pragma_name_tok = try pp.makePragmaToken(name_tok, operator_loc, arg_locs);
3116 try pp.addToken(pragma_name_tok);
3117 while (true) {
3118 const next_tok = tokenizer.next();
3119 if (next_tok.id == .whitespace) continue;
3120 if (next_tok.id == .eof) {
3121 try pp.addToken(.{
3122 .id = .nl,
3123 .loc = .{ .id = .generated },
3124 });
3125 break;
3126 }
3127 try pp.addToken(try pp.makePragmaToken(next_tok, operator_loc, arg_locs));
3128 if (next_tok.id == .nl) break;
3129 }
3130 if (pp.comp.getPragma(name)) |prag| unknown: {
3131 return prag.preprocessorCB(pp, pragma_start) catch |er| switch (er) {
3132 error.UnknownPragma => break :unknown,
3133 else => |e| return e,
3134 };
3135 }
3136 return pp.comp.addDiagnostic(.{
3137 .tag = .unknown_pragma,
3138 .loc = pragma_name_tok.loc,
3139 }, pragma_name_tok.expansionSlice());
3140}
3141
3142fn findIncludeFilenameToken(
3143 pp: *Preprocessor,
3144 first_token: RawToken,
3145 tokenizer: *Tokenizer,
3146 trailing_token_behavior: enum { ignore_trailing_tokens, expect_nl_eof },
3147) !TokenWithExpansionLocs {
3148 var first = first_token;
3149
3150 if (first.id == .angle_bracket_left) to_end: {
3151 // The tokenizer does not handle <foo> include strings so do it here.
3152 while (tokenizer.index < tokenizer.buf.len) : (tokenizer.index += 1) {
3153 switch (tokenizer.buf[tokenizer.index]) {
3154 '>' => {
3155 tokenizer.index += 1;
3156 first.end = tokenizer.index;
3157 first.id = .macro_string;
3158 break :to_end;
3159 },
3160 '\n' => break,
3161 else => {},
3162 }
3163 }
3164 try pp.comp.addDiagnostic(.{
3165 .tag = .header_str_closing,
3166 .loc = .{ .id = first.source, .byte_offset = tokenizer.index, .line = first.line },
3167 }, &.{});
3168 try pp.err(first, .header_str_match);
3169 }
3170
3171 const source_tok = tokFromRaw(first);
3172 const filename_tok, const expanded_trailing = switch (source_tok.id) {
3173 .string_literal, .macro_string => .{ source_tok, false },
3174 else => expanded: {
3175 // Try to expand if the argument is a macro.
3176 pp.top_expansion_buf.items.len = 0;
3177 defer for (pp.top_expansion_buf.items) |tok| TokenWithExpansionLocs.free(tok.expansion_locs, pp.gpa);
3178 try pp.top_expansion_buf.append(source_tok);
3179 pp.expansion_source_loc = source_tok.loc;
3180
3181 try pp.expandMacroExhaustive(tokenizer, &pp.top_expansion_buf, 0, 1, true, .non_expr);
3182 var trailing_toks: []const TokenWithExpansionLocs = &.{};
3183 const include_str = (try pp.reconstructIncludeString(pp.top_expansion_buf.items, &trailing_toks, tokFromRaw(first))) orelse {
3184 try pp.expectNl(tokenizer);
3185 return error.InvalidInclude;
3186 };
3187 const start = pp.comp.generated_buf.items.len;
3188 try pp.comp.generated_buf.appendSlice(pp.gpa, include_str);
3189
3190 break :expanded .{ try pp.makeGeneratedToken(start, switch (include_str[0]) {
3191 '"' => .string_literal,
3192 '<' => .macro_string,
3193 else => unreachable,
3194 }, pp.top_expansion_buf.items[0]), trailing_toks.len != 0 };
3195 },
3196 };
3197
3198 switch (trailing_token_behavior) {
3199 .expect_nl_eof => {
3200 // Error on extra tokens.
3201 const nl = tokenizer.nextNoWS();
3202 if ((nl.id != .nl and nl.id != .eof) or expanded_trailing) {
3203 skipToNl(tokenizer);
3204 try pp.comp.diagnostics.addExtra(pp.comp.langopts, .{
3205 .tag = .extra_tokens_directive_end,
3206 .loc = filename_tok.loc,
3207 }, filename_tok.expansionSlice(), false);
3208 }
3209 },
3210 .ignore_trailing_tokens => if (expanded_trailing) {
3211 try pp.comp.diagnostics.addExtra(pp.comp.langopts, .{
3212 .tag = .extra_tokens_directive_end,
3213 .loc = filename_tok.loc,
3214 }, filename_tok.expansionSlice(), false);
3215 },
3216 }
3217 return filename_tok;
3218}
3219
3220fn findIncludeSource(pp: *Preprocessor, tokenizer: *Tokenizer, first: RawToken, which: Compilation.WhichInclude) !Source {
3221 const filename_tok = try pp.findIncludeFilenameToken(first, tokenizer, .expect_nl_eof);
3222 defer TokenWithExpansionLocs.free(filename_tok.expansion_locs, pp.gpa);
3223
3224 // Check for empty filename.
3225 const tok_slice = pp.expandedSliceExtra(filename_tok, .single_macro_ws);
3226 if (tok_slice.len < 3) {
3227 try pp.err(first, .empty_filename);
3228 return error.InvalidInclude;
3229 }
3230
3231 // Find the file.
3232 const filename = tok_slice[1 .. tok_slice.len - 1];
3233 const include_type: Compilation.IncludeType = switch (filename_tok.id) {
3234 .string_literal => .quotes,
3235 .macro_string => .angle_brackets,
3236 else => unreachable,
3237 };
3238
3239 return (try pp.comp.findInclude(filename, first, include_type, which)) orelse
3240 return pp.fatalNotFound(filename_tok, filename);
3241}
3242
3243fn printLinemarker(
3244 pp: *Preprocessor,
3245 w: anytype,
3246 line_no: u32,
3247 source: Source,
3248 start_resume: enum(u8) { start, @"resume", none },
3249) !void {
3250 try w.writeByte('#');
3251 if (pp.linemarkers == .line_directives) try w.writeAll("line");
3252 try w.print(" {d} \"", .{line_no});
3253 for (source.path) |byte| switch (byte) {
3254 '\n' => try w.writeAll("\\n"),
3255 '\r' => try w.writeAll("\\r"),
3256 '\t' => try w.writeAll("\\t"),
3257 '\\' => try w.writeAll("\\\\"),
3258 '"' => try w.writeAll("\\\""),
3259 ' ', '!', '#'...'&', '('...'[', ']'...'~' => try w.writeByte(byte),
3260 // Use hex escapes for any non-ASCII/unprintable characters.
3261 // This ensures that the parsed version of this string will end up
3262 // containing the same bytes as the input regardless of encoding.
3263 else => {
3264 try w.writeAll("\\x");
3265 try std.fmt.formatInt(byte, 16, .lower, .{ .width = 2, .fill = '0' }, w);
3266 },
3267 };
3268 try w.writeByte('"');
3269 if (pp.linemarkers == .numeric_directives) {
3270 switch (start_resume) {
3271 .none => {},
3272 .start => try w.writeAll(" 1"),
3273 .@"resume" => try w.writeAll(" 2"),
3274 }
3275 switch (source.kind) {
3276 .user => {},
3277 .system => try w.writeAll(" 3"),
3278 .extern_c_system => try w.writeAll(" 3 4"),
3279 }
3280 }
3281 try w.writeByte('\n');
3282}
3283
3284// After how many empty lines are needed to replace them with linemarkers.
3285const collapse_newlines = 8;
3286
3287pub const DumpMode = enum {
3288 /// Standard preprocessor output; no macros
3289 result_only,
3290 /// Output only #define directives for all the macros defined during the execution of the preprocessor
3291 /// Only macros which are still defined at the end of preprocessing are printed.
3292 /// Only the most recent definition is printed
3293 /// Defines are printed in arbitrary order
3294 macros_only,
3295 /// Standard preprocessor output; but additionally output #define's and #undef's for macros as they are encountered
3296 macros_and_result,
3297 /// Same as macros_and_result, except only the macro name is printed for #define's
3298 macro_names_and_result,
3299};
3300
3301/// Pretty-print the macro define or undef at location `loc`.
3302/// We re-tokenize the directive because we are printing a macro that may have the same name as one in
3303/// `pp.defines` but a different definition (due to being #undef'ed and then redefined)
3304fn prettyPrintMacro(pp: *Preprocessor, w: anytype, loc: Source.Location, parts: enum { name_only, name_and_body }) !void {
3305 const source = pp.comp.getSource(loc.id);
3306 var tokenizer: Tokenizer = .{
3307 .buf = source.buf,
3308 .langopts = pp.comp.langopts,
3309 .source = source.id,
3310 .index = loc.byte_offset,
3311 };
3312 var prev_ws = false; // avoid printing multiple whitespace if /* */ comments are within the macro def
3313 var saw_name = false; // do not print comments before the name token is seen.
3314 while (true) {
3315 const tok = tokenizer.next();
3316 switch (tok.id) {
3317 .comment => {
3318 if (saw_name) {
3319 prev_ws = false;
3320 try w.print("{s}", .{pp.tokSlice(tok)});
3321 }
3322 },
3323 .nl, .eof => break,
3324 .whitespace => {
3325 if (!prev_ws) {
3326 try w.writeByte(' ');
3327 prev_ws = true;
3328 }
3329 },
3330 else => {
3331 prev_ws = false;
3332 try w.print("{s}", .{pp.tokSlice(tok)});
3333 },
3334 }
3335 if (tok.id == .identifier or tok.id == .extended_identifier) {
3336 if (parts == .name_only) break;
3337 saw_name = true;
3338 }
3339 }
3340}
3341
3342fn prettyPrintMacrosOnly(pp: *Preprocessor, w: anytype) !void {
3343 var it = pp.defines.valueIterator();
3344 while (it.next()) |macro| {
3345 if (macro.is_builtin) continue;
3346
3347 try w.writeAll("#define ");
3348 try pp.prettyPrintMacro(w, macro.loc, .name_and_body);
3349 try w.writeByte('\n');
3350 }
3351}
3352
3353/// Pretty print tokens and try to preserve whitespace.
3354pub fn prettyPrintTokens(pp: *Preprocessor, w: anytype, macro_dump_mode: DumpMode) !void {
3355 if (macro_dump_mode == .macros_only) {
3356 return pp.prettyPrintMacrosOnly(w);
3357 }
3358
3359 const tok_ids = pp.tokens.items(.id);
3360
3361 var i: u32 = 0;
3362 var last_nl = true;
3363 outer: while (true) : (i += 1) {
3364 var cur: Token = pp.tokens.get(i);
3365 switch (cur.id) {
3366 .eof => {
3367 if (!last_nl) try w.writeByte('\n');
3368 return;
3369 },
3370 .nl => {
3371 var newlines: u32 = 0;
3372 for (tok_ids[i..], i..) |id, j| {
3373 if (id == .nl) {
3374 newlines += 1;
3375 } else if (id == .eof) {
3376 if (!last_nl) try w.writeByte('\n');
3377 return;
3378 } else if (id != .whitespace) {
3379 if (pp.linemarkers == .none) {
3380 if (newlines < 2) break;
3381 } else if (newlines < collapse_newlines) {
3382 break;
3383 }
3384
3385 i = @intCast((j - 1) - @intFromBool(tok_ids[j - 1] == .whitespace));
3386 if (!last_nl) try w.writeAll("\n");
3387 if (pp.linemarkers != .none) {
3388 const next = pp.tokens.get(i);
3389 const source = pp.comp.getSource(next.loc.id);
3390 const line_col = source.lineCol(next.loc);
3391 try pp.printLinemarker(w, line_col.line_no, source, .none);
3392 last_nl = true;
3393 }
3394 continue :outer;
3395 }
3396 }
3397 last_nl = true;
3398 try w.writeAll("\n");
3399 },
3400 .keyword_pragma => {
3401 const pragma_name = pp.expandedSlice(pp.tokens.get(i + 1));
3402 const end_idx = mem.indexOfScalarPos(Token.Id, tok_ids, i, .nl) orelse i + 1;
3403 const pragma_len = @as(u32, @intCast(end_idx)) - i;
3404
3405 if (pp.comp.getPragma(pragma_name)) |prag| {
3406 if (!prag.shouldPreserveTokens(pp, i + 1)) {
3407 try w.writeByte('\n');
3408 i += pragma_len;
3409 cur = pp.tokens.get(i);
3410 continue;
3411 }
3412 }
3413 try w.writeAll("#pragma");
3414 i += 1;
3415 while (true) : (i += 1) {
3416 cur = pp.tokens.get(i);
3417 if (cur.id == .nl) {
3418 try w.writeByte('\n');
3419 last_nl = true;
3420 break;
3421 }
3422 try w.writeByte(' ');
3423 const slice = pp.expandedSlice(cur);
3424 try w.writeAll(slice);
3425 }
3426 },
3427 .whitespace => {
3428 var slice = pp.expandedSlice(cur);
3429 while (mem.indexOfScalar(u8, slice, '\n')) |some| {
3430 if (pp.linemarkers != .none) try w.writeByte('\n');
3431 slice = slice[some + 1 ..];
3432 }
3433 for (slice) |_| try w.writeByte(' ');
3434 last_nl = false;
3435 },
3436 .include_start => {
3437 const source = pp.comp.getSource(cur.loc.id);
3438
3439 try pp.printLinemarker(w, 1, source, .start);
3440 last_nl = true;
3441 },
3442 .include_resume => {
3443 const source = pp.comp.getSource(cur.loc.id);
3444 const line_col = source.lineCol(cur.loc);
3445 if (!last_nl) try w.writeAll("\n");
3446
3447 try pp.printLinemarker(w, line_col.line_no, source, .@"resume");
3448 last_nl = true;
3449 },
3450 .keyword_define, .keyword_undef => {
3451 switch (macro_dump_mode) {
3452 .macros_and_result, .macro_names_and_result => {
3453 try w.writeByte('#');
3454 try pp.prettyPrintMacro(w, cur.loc, if (macro_dump_mode == .macros_and_result) .name_and_body else .name_only);
3455 last_nl = false;
3456 },
3457 .result_only => unreachable, // `pp.store_macro_tokens` should be false for standard preprocessor output
3458 .macros_only => unreachable, // handled by prettyPrintMacrosOnly
3459 }
3460 },
3461 else => {
3462 const slice = pp.expandedSlice(cur);
3463 try w.writeAll(slice);
3464 last_nl = false;
3465 },
3466 }
3467 }
3468}
3469
3470test "Preserve pragma tokens sometimes" {
3471 const allocator = std.testing.allocator;
3472 const Test = struct {
3473 fn runPreprocessor(source_text: []const u8) ![]const u8 {
3474 var buf = std.ArrayList(u8).init(allocator);
3475 defer buf.deinit();
3476
3477 var comp = Compilation.init(allocator, std.fs.cwd());
3478 defer comp.deinit();
3479
3480 try comp.addDefaultPragmaHandlers();
3481
3482 var pp = Preprocessor.init(&comp);
3483 defer pp.deinit();
3484
3485 pp.preserve_whitespace = true;
3486 assert(pp.linemarkers == .none);
3487
3488 const test_runner_macros = try comp.addSourceFromBuffer("<test_runner>", source_text);
3489 const eof = try pp.preprocess(test_runner_macros);
3490 try pp.addToken(eof);
3491 try pp.prettyPrintTokens(buf.writer(), .result_only);
3492 return allocator.dupe(u8, buf.items);
3493 }
3494
3495 fn check(source_text: []const u8, expected: []const u8) !void {
3496 const output = try runPreprocessor(source_text);
3497 defer allocator.free(output);
3498
3499 try std.testing.expectEqualStrings(expected, output);
3500 }
3501 };
3502 const preserve_gcc_diagnostic =
3503 \\#pragma GCC diagnostic error "-Wnewline-eof"
3504 \\#pragma GCC warning error "-Wnewline-eof"
3505 \\int x;
3506 \\#pragma GCC ignored error "-Wnewline-eof"
3507 \\
3508 ;
3509 try Test.check(preserve_gcc_diagnostic, preserve_gcc_diagnostic);
3510
3511 const omit_once =
3512 \\#pragma once
3513 \\int x;
3514 \\#pragma once
3515 \\
3516 ;
3517 // TODO should only be one newline afterwards when emulating clang
3518 try Test.check(omit_once, "\nint x;\n\n");
3519
3520 const omit_poison =
3521 \\#pragma GCC poison foobar
3522 \\
3523 ;
3524 try Test.check(omit_poison, "\n");
3525}
3526
3527test "destringify" {
3528 const allocator = std.testing.allocator;
3529 const Test = struct {
3530 fn testDestringify(pp: *Preprocessor, stringified: []const u8, destringified: []const u8) !void {
3531 pp.char_buf.clearRetainingCapacity();
3532 try pp.char_buf.ensureUnusedCapacity(stringified.len);
3533 pp.destringify(stringified);
3534 try std.testing.expectEqualStrings(destringified, pp.char_buf.items);
3535 }
3536 };
3537 var comp = Compilation.init(allocator, std.fs.cwd());
3538 defer comp.deinit();
3539 var pp = Preprocessor.init(&comp);
3540 defer pp.deinit();
3541
3542 try Test.testDestringify(&pp, "hello\tworld\n", "hello\tworld\n");
3543 try Test.testDestringify(&pp,
3544 \\ \"FOO BAR BAZ\"
3545 ,
3546 \\ "FOO BAR BAZ"
3547 );
3548 try Test.testDestringify(&pp,
3549 \\ \\t\\n
3550 \\
3551 ,
3552 \\ \t\n
3553 \\
3554 );
3555}
3556
3557test "Include guards" {
3558 const Test = struct {
3559 /// This is here so that when #elifdef / #elifndef are added we don't forget
3560 /// to test that they don't accidentally break include guard detection
3561 fn pairsWithIfndef(tok_id: RawToken.Id) bool {
3562 return switch (tok_id) {
3563 .keyword_elif,
3564 .keyword_elifdef,
3565 .keyword_elifndef,
3566 .keyword_else,
3567 => true,
3568
3569 .keyword_include,
3570 .keyword_include_next,
3571 .keyword_embed,
3572 .keyword_define,
3573 .keyword_defined,
3574 .keyword_undef,
3575 .keyword_ifdef,
3576 .keyword_ifndef,
3577 .keyword_error,
3578 .keyword_warning,
3579 .keyword_pragma,
3580 .keyword_line,
3581 .keyword_endif,
3582 => false,
3583 else => unreachable,
3584 };
3585 }
3586
3587 fn skippable(tok_id: RawToken.Id) bool {
3588 return switch (tok_id) {
3589 .keyword_defined, .keyword_va_args, .keyword_va_opt, .keyword_endif => true,
3590 else => false,
3591 };
3592 }
3593
3594 fn testIncludeGuard(allocator: std.mem.Allocator, comptime template: []const u8, tok_id: RawToken.Id, expected_guards: u32) !void {
3595 var comp = Compilation.init(allocator, std.fs.cwd());
3596 defer comp.deinit();
3597 var pp = Preprocessor.init(&comp);
3598 defer pp.deinit();
3599
3600 const path = try std.fs.path.join(allocator, &.{ ".", "bar.h" });
3601 defer allocator.free(path);
3602
3603 _ = try comp.addSourceFromBuffer(path, "int bar = 5;\n");
3604
3605 var buf = std.ArrayList(u8).init(allocator);
3606 defer buf.deinit();
3607
3608 var writer = buf.writer();
3609 switch (tok_id) {
3610 .keyword_include, .keyword_include_next => try writer.print(template, .{ tok_id.lexeme().?, " \"bar.h\"" }),
3611 .keyword_define, .keyword_undef => try writer.print(template, .{ tok_id.lexeme().?, " BAR" }),
3612 .keyword_ifndef,
3613 .keyword_ifdef,
3614 .keyword_elifdef,
3615 .keyword_elifndef,
3616 => try writer.print(template, .{ tok_id.lexeme().?, " BAR\n#endif" }),
3617 else => try writer.print(template, .{ tok_id.lexeme().?, "" }),
3618 }
3619 const source = try comp.addSourceFromBuffer("test.h", buf.items);
3620 _ = try pp.preprocess(source);
3621
3622 try std.testing.expectEqual(expected_guards, pp.include_guards.count());
3623 }
3624 };
3625 const tags = std.meta.tags(RawToken.Id);
3626 for (tags) |tag| {
3627 if (Test.skippable(tag)) continue;
3628 var copy = tag;
3629 copy.simplifyMacroKeyword();
3630 if (copy != tag or tag == .keyword_else) {
3631 const inside_ifndef_template =
3632 \\//Leading comment (should be ignored)
3633 \\
3634 \\#ifndef FOO
3635 \\#{s}{s}
3636 \\#endif
3637 ;
3638 const expected_guards: u32 = if (Test.pairsWithIfndef(tag)) 0 else 1;
3639 try Test.testIncludeGuard(std.testing.allocator, inside_ifndef_template, tag, expected_guards);
3640
3641 const outside_ifndef_template =
3642 \\#ifndef FOO
3643 \\#endif
3644 \\#{s}{s}
3645 ;
3646 try Test.testIncludeGuard(std.testing.allocator, outside_ifndef_template, tag, 0);
3647 }
3648 }
3649}
src/Compilation.zig+31-41
...@@ -4356,7 +4356,6 @@ pub fn cImport(comp: *Compilation, c_src: []const u8, owner_mod: *Package.Module...@@ -4356,7 +4356,6 @@ pub fn cImport(comp: *Compilation, c_src: []const u8, owner_mod: *Package.Module
43564356
4357 man.hash.add(@as(u16, 0xb945)); // Random number to distinguish translate-c from compiling C objects4357 man.hash.add(@as(u16, 0xb945)); // Random number to distinguish translate-c from compiling C objects
4358 man.hash.addBytes(c_src);4358 man.hash.addBytes(c_src);
4359 man.hash.add(comp.config.c_frontend);
43604359
4361 // If the previous invocation resulted in clang errors, we will see a hit4360 // If the previous invocation resulted in clang errors, we will see a hit
4362 // here with 0 files in the manifest, in which case it is actually a miss.4361 // here with 0 files in the manifest, in which case it is actually a miss.
...@@ -4393,7 +4392,7 @@ pub fn cImport(comp: *Compilation, c_src: []const u8, owner_mod: *Package.Module...@@ -4393,7 +4392,7 @@ pub fn cImport(comp: *Compilation, c_src: []const u8, owner_mod: *Package.Module
4393 var argv = std.ArrayList([]const u8).init(comp.gpa);4392 var argv = std.ArrayList([]const u8).init(comp.gpa);
4394 defer argv.deinit();4393 defer argv.deinit();
43954394
4396 try argv.append(@tagName(comp.config.c_frontend)); // argv[0] is program name, actual args start at [1]4395 try argv.append("clang"); // argv[0] is program name, actual args start at [1]
4397 try comp.addTranslateCCArgs(arena, &argv, .c, out_dep_path, owner_mod);4396 try comp.addTranslateCCArgs(arena, &argv, .c, out_dep_path, owner_mod);
43984397
4399 try argv.append(out_h_path);4398 try argv.append(out_h_path);
...@@ -4401,43 +4400,37 @@ pub fn cImport(comp: *Compilation, c_src: []const u8, owner_mod: *Package.Module...@@ -4401,43 +4400,37 @@ pub fn cImport(comp: *Compilation, c_src: []const u8, owner_mod: *Package.Module
4401 if (comp.verbose_cc) {4400 if (comp.verbose_cc) {
4402 dump_argv(argv.items);4401 dump_argv(argv.items);
4403 }4402 }
4404 var tree = switch (comp.config.c_frontend) {4403 var tree = tree: {
4405 .aro => tree: {4404 if (!build_options.have_llvm) unreachable;
4406 if (true) @panic("TODO");4405 const translate_c = @import("translate_c.zig");
4407 break :tree undefined;4406
4408 },4407 // Convert to null terminated args.
4409 .clang => tree: {4408 const new_argv_with_sentinel = try arena.alloc(?[*:0]const u8, argv.items.len + 1);
4410 if (!build_options.have_llvm) unreachable;4409 new_argv_with_sentinel[argv.items.len] = null;
4411 const translate_c = @import("translate_c.zig");4410 const new_argv = new_argv_with_sentinel[0..argv.items.len :null];
44124411 for (argv.items, 0..) |arg, i| {
4413 // Convert to null terminated args.4412 new_argv[i] = try arena.dupeZ(u8, arg);
4414 const new_argv_with_sentinel = try arena.alloc(?[*:0]const u8, argv.items.len + 1);4413 }
4415 new_argv_with_sentinel[argv.items.len] = null;
4416 const new_argv = new_argv_with_sentinel[0..argv.items.len :null];
4417 for (argv.items, 0..) |arg, i| {
4418 new_argv[i] = try arena.dupeZ(u8, arg);
4419 }
44204414
4421 const c_headers_dir_path_z = try comp.zig_lib_directory.joinZ(arena, &[_][]const u8{"include"});4415 const c_headers_dir_path_z = try comp.zig_lib_directory.joinZ(arena, &[_][]const u8{"include"});
4422 var errors = std.zig.ErrorBundle.empty;4416 var errors = std.zig.ErrorBundle.empty;
4423 errdefer errors.deinit(comp.gpa);4417 errdefer errors.deinit(comp.gpa);
4424 break :tree translate_c.translate(4418 break :tree translate_c.translate(
4425 comp.gpa,4419 comp.gpa,
4426 new_argv.ptr,4420 new_argv.ptr,
4427 new_argv.ptr + new_argv.len,4421 new_argv.ptr + new_argv.len,
4428 &errors,4422 &errors,
4429 c_headers_dir_path_z,4423 c_headers_dir_path_z,
4430 ) catch |err| switch (err) {4424 ) catch |err| switch (err) {
4431 error.OutOfMemory => return error.OutOfMemory,4425 error.OutOfMemory => return error.OutOfMemory,
4432 error.SemanticAnalyzeFail => {4426 error.SemanticAnalyzeFail => {
4433 return CImportResult{4427 return CImportResult{
4434 .digest = undefined,4428 .digest = undefined,
4435 .cache_hit = actual_hit,4429 .cache_hit = actual_hit,
4436 .errors = errors,4430 .errors = errors,
4437 };4431 };
4438 },4432 },
4439 };4433 };
4440 },
4441 };4434 };
4442 defer tree.deinit(comp.gpa);4435 defer tree.deinit(comp.gpa);
44434436
...@@ -4616,9 +4609,6 @@ fn reportRetryableEmbedFileError(...@@ -4616,9 +4609,6 @@ fn reportRetryableEmbedFileError(
4616}4609}
46174610
4618fn updateCObject(comp: *Compilation, c_object: *CObject, c_obj_prog_node: std.Progress.Node) !void {4611fn updateCObject(comp: *Compilation, c_object: *CObject, c_obj_prog_node: std.Progress.Node) !void {
4619 if (comp.config.c_frontend == .aro) {
4620 return comp.failCObj(c_object, "aro does not support compiling C objects yet", .{});
4621 }
4622 if (!build_options.have_llvm) {4612 if (!build_options.have_llvm) {
4623 return comp.failCObj(c_object, "clang not available: compiler built without LLVM extensions", .{});4613 return comp.failCObj(c_object, "clang not available: compiler built without LLVM extensions", .{});
4624 }4614 }
src/Compilation/Config.zig-14
...@@ -47,7 +47,6 @@ use_lib_llvm: bool,...@@ -47,7 +47,6 @@ use_lib_llvm: bool,
47/// objects. Otherwise (depending on `use_llvm`) linker code directly outputs47/// objects. Otherwise (depending on `use_llvm`) linker code directly outputs
48/// and updates the final binary.48/// and updates the final binary.
49use_lld: bool,49use_lld: bool,
50c_frontend: CFrontend,
51lto: bool,50lto: bool,
52/// WASI-only. Type of WASI execution model ("command" or "reactor").51/// WASI-only. Type of WASI execution model ("command" or "reactor").
53/// Always set to `command` for non-WASI targets.52/// Always set to `command` for non-WASI targets.
...@@ -272,18 +271,6 @@ pub fn resolve(options: Options) ResolveError!Config {...@@ -272,18 +271,6 @@ pub fn resolve(options: Options) ResolveError!Config {
272 break :b true;271 break :b true;
273 };272 };
274273
275 // Make a decision on whether to use Clang or Aro for translate-c and compiling C files.
276 const c_frontend: CFrontend = b: {
277 if (!build_options.have_llvm) {
278 if (options.use_clang == true) return error.ClangUnavailable;
279 break :b .aro;
280 }
281 if (options.use_clang) |clang| {
282 break :b if (clang) .clang else .aro;
283 }
284 break :b .clang;
285 };
286
287 const lto = b: {274 const lto = b: {
288 if (!use_lld) {275 if (!use_lld) {
289 // zig ld LTO support is tracked by276 // zig ld LTO support is tracked by
...@@ -507,7 +494,6 @@ pub fn resolve(options: Options) ResolveError!Config {...@@ -507,7 +494,6 @@ pub fn resolve(options: Options) ResolveError!Config {
507 .import_memory = import_memory,494 .import_memory = import_memory,
508 .export_memory = export_memory,495 .export_memory = export_memory,
509 .shared_memory = shared_memory,496 .shared_memory = shared_memory,
510 .c_frontend = c_frontend,
511 .use_llvm = use_llvm,497 .use_llvm = use_llvm,
512 .use_lib_llvm = use_lib_llvm,498 .use_lib_llvm = use_lib_llvm,
513 .use_lld = use_lld,499 .use_lld = use_lld,
src/Package/Module.zig+2-5
...@@ -255,8 +255,7 @@ pub fn create(arena: Allocator, options: CreateOptions) !*Package.Module {...@@ -255,8 +255,7 @@ pub fn create(arena: Allocator, options: CreateOptions) !*Package.Module {
255 };255 };
256256
257 const stack_protector: u32 = sp: {257 const stack_protector: u32 = sp: {
258 const use_zig_backend = options.global.have_zcu or258 const use_zig_backend = options.global.have_zcu;
259 (options.global.any_c_source_files and options.global.c_frontend == .aro);
260 if (use_zig_backend and !target_util.supportsStackProtector(target, zig_backend)) {259 if (use_zig_backend and !target_util.supportsStackProtector(target, zig_backend)) {
261 if (options.inherited.stack_protector) |x| {260 if (options.inherited.stack_protector) |x| {
262 if (x > 0) return error.StackProtectorUnsupportedByTarget;261 if (x > 0) return error.StackProtectorUnsupportedByTarget;
...@@ -264,9 +263,7 @@ pub fn create(arena: Allocator, options: CreateOptions) !*Package.Module {...@@ -264,9 +263,7 @@ pub fn create(arena: Allocator, options: CreateOptions) !*Package.Module {
264 break :sp 0;263 break :sp 0;
265 }264 }
266265
267 if (options.global.any_c_source_files and options.global.c_frontend == .clang and266 if (options.global.any_c_source_files and !target_util.clangSupportsStackProtector(target)) {
268 !target_util.clangSupportsStackProtector(target))
269 {
270 if (options.inherited.stack_protector) |x| {267 if (options.inherited.stack_protector) |x| {
271 if (x > 0) return error.StackProtectorUnsupportedByTarget;268 if (x > 0) return error.StackProtectorUnsupportedByTarget;
272 }269 }
src/main.zig+33-54
...@@ -4468,6 +4468,7 @@ fn cmdTranslateC(...@@ -4468,6 +4468,7 @@ fn cmdTranslateC(
4468 file_system_inputs: ?*std.ArrayListUnmanaged(u8),4468 file_system_inputs: ?*std.ArrayListUnmanaged(u8),
4469 prog_node: std.Progress.Node,4469 prog_node: std.Progress.Node,
4470) !void {4470) !void {
4471 _ = prog_node;
4471 dev.check(.translate_c_command);4472 dev.check(.translate_c_command);
44724473
4473 const color: Color = .auto;4474 const color: Color = .auto;
...@@ -4481,7 +4482,6 @@ fn cmdTranslateC(...@@ -4481,7 +4482,6 @@ fn cmdTranslateC(
4481 defer man.deinit();4482 defer man.deinit();
44824483
4483 man.hash.add(@as(u16, 0xb945)); // Random number to distinguish translate-c from compiling C objects4484 man.hash.add(@as(u16, 0xb945)); // Random number to distinguish translate-c from compiling C objects
4484 man.hash.add(comp.config.c_frontend);
4485 Compilation.cache_helpers.hashCSource(&man, c_source_file) catch |err| {4485 Compilation.cache_helpers.hashCSource(&man, c_source_file) catch |err| {
4486 fatal("unable to process '{s}': {s}", .{ c_source_file.src_path, @errorName(err) });4486 fatal("unable to process '{s}': {s}", .{ c_source_file.src_path, @errorName(err) });
4487 };4487 };
...@@ -4495,20 +4495,14 @@ fn cmdTranslateC(...@@ -4495,20 +4495,14 @@ fn cmdTranslateC(
4495 } else digest: {4495 } else digest: {
4496 if (fancy_output) |p| p.cache_hit = false;4496 if (fancy_output) |p| p.cache_hit = false;
4497 var argv = std.ArrayList([]const u8).init(arena);4497 var argv = std.ArrayList([]const u8).init(arena);
4498 switch (comp.config.c_frontend) {4498 try argv.append("clang"); // argv[0] is program name, actual args start at [1]
4499 .aro => {},
4500 .clang => {
4501 // argv[0] is program name, actual args start at [1]
4502 try argv.append(@tagName(comp.config.c_frontend));
4503 },
4504 }
45054499
4506 var zig_cache_tmp_dir = try comp.local_cache_directory.handle.makeOpenPath("tmp", .{});4500 var zig_cache_tmp_dir = try comp.local_cache_directory.handle.makeOpenPath("tmp", .{});
4507 defer zig_cache_tmp_dir.close();4501 defer zig_cache_tmp_dir.close();
45084502
4509 const ext = Compilation.classifyFileExt(c_source_file.src_path);4503 const ext = Compilation.classifyFileExt(c_source_file.src_path);
4510 const out_dep_path: ?[]const u8 = blk: {4504 const out_dep_path: ?[]const u8 = blk: {
4511 if (comp.config.c_frontend == .aro or comp.disable_c_depfile or !ext.clangSupportsDepFile())4505 if (comp.disable_c_depfile or !ext.clangSupportsDepFile())
4512 break :blk null;4506 break :blk null;
45134507
4514 const c_src_basename = fs.path.basename(c_source_file.src_path);4508 const c_src_basename = fs.path.basename(c_source_file.src_path);
...@@ -4517,9 +4511,7 @@ fn cmdTranslateC(...@@ -4517,9 +4511,7 @@ fn cmdTranslateC(
4517 break :blk out_dep_path;4511 break :blk out_dep_path;
4518 };4512 };
45194513
4520 // TODO4514 try comp.addTranslateCCArgs(arena, &argv, ext, out_dep_path, comp.root_mod);
4521 if (comp.config.c_frontend != .aro)
4522 try comp.addTranslateCCArgs(arena, &argv, ext, out_dep_path, comp.root_mod);
4523 try argv.append(c_source_file.src_path);4515 try argv.append(c_source_file.src_path);
45244516
4525 if (comp.verbose_cc) {4517 if (comp.verbose_cc) {
...@@ -4531,49 +4523,36 @@ fn cmdTranslateC(...@@ -4531,49 +4523,36 @@ fn cmdTranslateC(
4531 error_bundle: std.zig.ErrorBundle,4523 error_bundle: std.zig.ErrorBundle,
4532 };4524 };
45334525
4534 const result: Result = switch (comp.config.c_frontend) {4526 const result: Result = f: {
4535 .aro => f: {4527 if (!build_options.have_llvm) unreachable;
4536 var stdout: []u8 = undefined;4528 const translate_c = @import("translate_c.zig");
4537 try jitCmd(comp.gpa, arena, argv.items, .{4529
4538 .cmd_name = "aro_translate_c",4530 // Convert to null terminated args.
4539 .root_src_path = "aro_translate_c.zig",4531 const clang_args_len = argv.items.len + c_source_file.extra_flags.len;
4540 .depend_on_aro = true,4532 const new_argv_with_sentinel = try arena.alloc(?[*:0]const u8, clang_args_len + 1);
4541 .capture = &stdout,4533 new_argv_with_sentinel[clang_args_len] = null;
4542 .progress_node = prog_node,4534 const new_argv = new_argv_with_sentinel[0..clang_args_len :null];
4543 });4535 for (argv.items, 0..) |arg, i| {
4544 break :f .{ .success = stdout };4536 new_argv[i] = try arena.dupeZ(u8, arg);
4545 },4537 }
4546 .clang => f: {4538 for (c_source_file.extra_flags, 0..) |arg, i| {
4547 if (!build_options.have_llvm) unreachable;4539 new_argv[argv.items.len + i] = try arena.dupeZ(u8, arg);
4548 const translate_c = @import("translate_c.zig");4540 }
4549
4550 // Convert to null terminated args.
4551 const clang_args_len = argv.items.len + c_source_file.extra_flags.len;
4552 const new_argv_with_sentinel = try arena.alloc(?[*:0]const u8, clang_args_len + 1);
4553 new_argv_with_sentinel[clang_args_len] = null;
4554 const new_argv = new_argv_with_sentinel[0..clang_args_len :null];
4555 for (argv.items, 0..) |arg, i| {
4556 new_argv[i] = try arena.dupeZ(u8, arg);
4557 }
4558 for (c_source_file.extra_flags, 0..) |arg, i| {
4559 new_argv[argv.items.len + i] = try arena.dupeZ(u8, arg);
4560 }
45614541
4562 const c_headers_dir_path_z = try comp.zig_lib_directory.joinZ(arena, &[_][]const u8{"include"});4542 const c_headers_dir_path_z = try comp.zig_lib_directory.joinZ(arena, &[_][]const u8{"include"});
4563 var errors = std.zig.ErrorBundle.empty;4543 var errors = std.zig.ErrorBundle.empty;
4564 var tree = translate_c.translate(4544 var tree = translate_c.translate(
4565 comp.gpa,4545 comp.gpa,
4566 new_argv.ptr,4546 new_argv.ptr,
4567 new_argv.ptr + new_argv.len,4547 new_argv.ptr + new_argv.len,
4568 &errors,4548 &errors,
4569 c_headers_dir_path_z,4549 c_headers_dir_path_z,
4570 ) catch |err| switch (err) {4550 ) catch |err| switch (err) {
4571 error.OutOfMemory => return error.OutOfMemory,4551 error.OutOfMemory => return error.OutOfMemory,
4572 error.SemanticAnalyzeFail => break :f .{ .error_bundle = errors },4552 error.SemanticAnalyzeFail => break :f .{ .error_bundle = errors },
4573 };4553 };
4574 defer tree.deinit(comp.gpa);4554 defer tree.deinit(comp.gpa);
4575 break :f .{ .success = try tree.render(arena) };4555 break :f .{ .success = try tree.render(arena) };
4576 },
4577 };4556 };
45784557
4579 if (out_dep_path) |dep_file_path| add_deps: {4558 if (out_dep_path) |dep_file_path| add_deps: {
src/mingw.zig+30-29
...@@ -282,50 +282,51 @@ pub fn buildImportLib(comp: *Compilation, lib_name: []const u8) !void {...@@ -282,50 +282,51 @@ pub fn buildImportLib(comp: *Compilation, lib_name: []const u8) !void {
282 defer o_dir.close();282 defer o_dir.close();
283283
284 const final_def_basename = try std.fmt.allocPrint(arena, "{s}.def", .{lib_name});284 const final_def_basename = try std.fmt.allocPrint(arena, "{s}.def", .{lib_name});
285 const def_final_path = try comp.global_cache_directory.join(arena, &[_][]const u8{285 const def_final_path: Cache.Path = .{
286 "o", &digest, final_def_basename,286 .root_dir = comp.global_cache_directory,
287 });287 .sub_path = try std.fs.path.join(arena, &.{ "o", &digest, final_def_basename }),
288
289 const target_defines = switch (target.cpu.arch) {
290 .thumb => "#define DEF_ARM32\n",
291 .aarch64 => "#define DEF_ARM64\n",
292 .x86 => "#define DEF_I386\n",
293 .x86_64 => "#define DEF_X64\n",
294 else => unreachable,
295 };288 };
296289
297 const aro = @import("aro");290 var preprocessor: std.zig.Preprocessor = .{
298 var aro_comp = aro.Compilation.init(gpa, std.fs.cwd());291 .linemarkers = .none,
299 defer aro_comp.deinit();292 .preserve_whitespace = true,
293 };
300294
301 const include_dir = try comp.zig_lib_directory.join(arena, &[_][]const u8{ "libc", "mingw", "def-include" });295 const include_path: Cache.Path = .{
296 .root_dir = comp.zig_lib_directory,
297 .sub_path = try std.fs.path.join(arena, &.{ "libc", "mingw", "def-include" }),
298 };
302299
303 if (comp.verbose_cc) print: {300 if (comp.verbose_cc) print: {
304 std.debug.lockStdErr();301 std.debug.lockStdErr();
305 defer std.debug.unlockStdErr();302 defer std.debug.unlockStdErr();
306 const stderr = std.io.getStdErr().writer();303 const stderr = std.io.getStdErr().writer();
307 nosuspend stderr.print("def file: {s}\n", .{def_file_path}) catch break :print;304 nosuspend stderr.print("def file: {s}\n", .{def_file_path}) catch break :print;
308 nosuspend stderr.print("include dir: {s}\n", .{include_dir}) catch break :print;305 nosuspend stderr.print("include path: {}\n", .{include_path}) catch break :print;
309 nosuspend stderr.print("output path: {s}\n", .{def_final_path}) catch break :print;306 nosuspend stderr.print("output path: {}\n", .{def_final_path}) catch break :print;
310 }307 }
311308
312 try aro_comp.include_dirs.append(gpa, include_dir);309 try preprocessor.addIncludeDirectory(arena, include_path);
313310
314 const builtin_macros = try aro_comp.generateBuiltinMacros(.include_system_defines);311 const builtin_macros = try preprocessor.generateBuiltinMacros(.include_system_defines);
315 const user_macros = try aro_comp.addSourceFromBuffer("<command line>", target_defines);
316 const def_file_source = try aro_comp.addSourceFromPath(def_file_path);
317312
318 var pp = aro.Preprocessor.init(&aro_comp);313 const target_defines = switch (target.cpu.arch) {
319 defer pp.deinit();314 .thumb => "#define DEF_ARM32\n",
320 pp.linemarkers = .none;315 .aarch64 => "#define DEF_ARM64\n",
321 pp.preserve_whitespace = true;316 .x86 => "#define DEF_I386\n",
317 .x86_64 => "#define DEF_X64\n",
318 else => unreachable,
319 };
320 const user_macros = try preprocessor.addSourceFromBuffer("<command line>", target_defines);
321 const def_file_source = try preprocessor.addSourceFromPath(def_file_path);
322322
323 try pp.preprocessSources(&.{ def_file_source, builtin_macros, user_macros });323 try preprocessor.preprocessSources(&.{ def_file_source, builtin_macros, user_macros });
324324
325 for (aro_comp.diagnostics.list.items) |diagnostic| {325 for (preprocessor.diagnostics.list.items) |diagnostic| {
326 if (diagnostic.kind == .@"fatal error" or diagnostic.kind == .@"error") {326 if (diagnostic.kind == .@"fatal error" or diagnostic.kind == .@"error") {
327 aro.Diagnostics.render(&aro_comp, std.io.tty.detectConfig(std.io.getStdErr()));327 // TODO report this instead of printing to stderr
328 return error.AroPreprocessorFailed;328 preprocessor.renderDiagnostics(std.io.tty.detectConfig(std.io.getStdErr()));
329 return error.PreprocessorFailed;
329 }330 }
330 }331 }
331332
...@@ -333,7 +334,7 @@ pub fn buildImportLib(comp: *Compilation, lib_name: []const u8) !void {...@@ -333,7 +334,7 @@ pub fn buildImportLib(comp: *Compilation, lib_name: []const u8) !void {
333 // new scope to ensure definition file is written before passing the path to WriteImportLibrary334 // new scope to ensure definition file is written before passing the path to WriteImportLibrary
334 const def_final_file = try o_dir.createFile(final_def_basename, .{ .truncate = true });335 const def_final_file = try o_dir.createFile(final_def_basename, .{ .truncate = true });
335 defer def_final_file.close();336 defer def_final_file.close();
336 try pp.prettyPrintTokens(def_final_file.writer(), .result_only);337 try preprocessor.prettyPrintTokens(def_final_file.writer(), .result_only);
337 }338 }
338339
339 const lib_final_path = try std.fs.path.join(gpa, &.{ "o", &digest, final_lib_basename });340 const lib_final_path = try std.fs.path.join(gpa, &.{ "o", &digest, final_lib_basename });
src/translate_c.zig+15-15
...@@ -5,22 +5,22 @@ const mem = std.mem;...@@ -5,22 +5,22 @@ const mem = std.mem;
5const math = std.math;5const math = std.math;
6const meta = std.meta;6const meta = std.meta;
7const clang = @import("clang.zig");7const clang = @import("clang.zig");
8const aro = @import("aro");8const ast = @import("translate_c/ast.zig");
9const CToken = aro.Tokenizer.Token;
10const Node = ast.Node;9const Node = ast.Node;
11const Tag = Node.Tag;10const Tag = Node.Tag;
12const common = @import("aro_translate_c");11
13const ast = common.ast;12const aro = @import("translate_c/aro.zig");
14const Error = common.Error;13const CToken = aro.Tokenizer.Token;
15const MacroProcessingError = common.MacroProcessingError;14const Error = aro.Error;
16const TypeError = common.TypeError;15const MacroProcessingError = aro.MacroProcessingError;
17const TransError = common.TransError;16const TypeError = aro.TypeError;
18const SymbolTable = common.SymbolTable;17const TransError = aro.TransError;
19const AliasList = common.AliasList;18const SymbolTable = aro.SymbolTable;
20const ResultUsed = common.ResultUsed;19const AliasList = aro.AliasList;
21const Scope = common.ScopeExtra(Context, clang.QualType);20const ResultUsed = aro.ResultUsed;
22const PatternList = common.PatternList;21const Scope = aro.ScopeExtra(Context, clang.QualType);
23const MacroSlicer = common.MacroSlicer;22const PatternList = aro.PatternList;
23const MacroSlicer = aro.MacroSlicer;
2424
25pub const Context = struct {25pub const Context = struct {
26 gpa: mem.Allocator,26 gpa: mem.Allocator,
...@@ -5299,7 +5299,7 @@ fn transPreprocessorEntities(c: *Context, unit: *clang.ASTUnit) Error!void {...@@ -5299,7 +5299,7 @@ fn transPreprocessorEntities(c: *Context, unit: *clang.ASTUnit) Error!void {
52995299
5300 const source = try getMacroText(unit, c, macro);5300 const source = try getMacroText(unit, c, macro);
53015301
5302 try common.tokenizeMacro(source, &tok_list);5302 try aro.tokenizeMacro(source, &tok_list);
53035303
5304 var macro_ctx = MacroCtx{5304 var macro_ctx = MacroCtx{
5305 .source = source,5305 .source = source,
src/translate_c/Tokenizer.zig created+1807
...@@ -0,0 +1,1807 @@
1const std = @import("std");
2const assert = std.debug.assert;
3const Source = @import("Source.zig");
4const LangOpts = @import("LangOpts.zig");
5
6pub const Token = struct {
7 id: Id,
8 source: Source.Id,
9 start: u32 = 0,
10 end: u32 = 0,
11 line: u32 = 0,
12
13 pub const Id = enum(u8) {
14 invalid,
15 nl,
16 whitespace,
17 eof,
18 /// identifier containing solely basic character set characters
19 identifier,
20 /// identifier with at least one extended character
21 extended_identifier,
22
23 // string literals with prefixes
24 string_literal,
25 string_literal_utf_16,
26 string_literal_utf_8,
27 string_literal_utf_32,
28 string_literal_wide,
29
30 /// Any string literal with an embedded newline or EOF
31 /// Always a parser error; by default just a warning from preprocessor
32 unterminated_string_literal,
33
34 // <foobar> only generated by preprocessor
35 macro_string,
36
37 // char literals with prefixes
38 char_literal,
39 char_literal_utf_8,
40 char_literal_utf_16,
41 char_literal_utf_32,
42 char_literal_wide,
43
44 /// Any character literal with nothing inside the quotes
45 /// Always a parser error; by default just a warning from preprocessor
46 empty_char_literal,
47
48 /// Any character literal with an embedded newline or EOF
49 /// Always a parser error; by default just a warning from preprocessor
50 unterminated_char_literal,
51
52 /// `/* */` style comment without a closing `*/` before EOF
53 unterminated_comment,
54
55 /// Integer literal tokens generated by preprocessor.
56 one,
57 zero,
58
59 bang,
60 bang_equal,
61 pipe,
62 pipe_pipe,
63 pipe_equal,
64 equal,
65 equal_equal,
66 l_paren,
67 r_paren,
68 l_brace,
69 r_brace,
70 l_bracket,
71 r_bracket,
72 period,
73 ellipsis,
74 caret,
75 caret_equal,
76 plus,
77 plus_plus,
78 plus_equal,
79 minus,
80 minus_minus,
81 minus_equal,
82 asterisk,
83 asterisk_equal,
84 percent,
85 percent_equal,
86 arrow,
87 colon,
88 colon_colon,
89 semicolon,
90 slash,
91 slash_equal,
92 comma,
93 ampersand,
94 ampersand_ampersand,
95 ampersand_equal,
96 question_mark,
97 angle_bracket_left,
98 angle_bracket_left_equal,
99 angle_bracket_angle_bracket_left,
100 angle_bracket_angle_bracket_left_equal,
101 angle_bracket_right,
102 angle_bracket_right_equal,
103 angle_bracket_angle_bracket_right,
104 angle_bracket_angle_bracket_right_equal,
105 tilde,
106 hash,
107 hash_hash,
108
109 /// Special token to speed up preprocessing, `loc.end` will be an index to the param list.
110 macro_param,
111 /// Special token to signal that the argument must be replaced without expansion (e.g. in concatenation)
112 macro_param_no_expand,
113 /// Special token to speed up preprocessing, `loc.end` will be an index to the param list.
114 stringify_param,
115 /// Same as stringify_param, but for var args
116 stringify_va_args,
117 /// Special macro whitespace, always equal to a single space
118 macro_ws,
119 /// Special token for implementing __has_attribute
120 macro_param_has_attribute,
121 /// Special token for implementing __has_c_attribute
122 macro_param_has_c_attribute,
123 /// Special token for implementing __has_declspec_attribute
124 macro_param_has_declspec_attribute,
125 /// Special token for implementing __has_warning
126 macro_param_has_warning,
127 /// Special token for implementing __has_feature
128 macro_param_has_feature,
129 /// Special token for implementing __has_extension
130 macro_param_has_extension,
131 /// Special token for implementing __has_builtin
132 macro_param_has_builtin,
133 /// Special token for implementing __has_include
134 macro_param_has_include,
135 /// Special token for implementing __has_include_next
136 macro_param_has_include_next,
137 /// Special token for implementing __has_embed
138 macro_param_has_embed,
139 /// Special token for implementing __is_identifier
140 macro_param_is_identifier,
141 /// Special token for implementing __FILE__
142 macro_file,
143 /// Special token for implementing __LINE__
144 macro_line,
145 /// Special token for implementing __COUNTER__
146 macro_counter,
147 /// Special token for implementing _Pragma
148 macro_param_pragma_operator,
149
150 /// Special identifier for implementing __func__
151 macro_func,
152 /// Special identifier for implementing __FUNCTION__
153 macro_function,
154 /// Special identifier for implementing __PRETTY_FUNCTION__
155 macro_pretty_func,
156
157 keyword_auto,
158 keyword_auto_type,
159 keyword_break,
160 keyword_case,
161 keyword_char,
162 keyword_const,
163 keyword_continue,
164 keyword_default,
165 keyword_do,
166 keyword_double,
167 keyword_else,
168 keyword_enum,
169 keyword_extern,
170 keyword_float,
171 keyword_for,
172 keyword_goto,
173 keyword_if,
174 keyword_int,
175 keyword_long,
176 keyword_register,
177 keyword_return,
178 keyword_short,
179 keyword_signed,
180 keyword_signed1,
181 keyword_signed2,
182 keyword_sizeof,
183 keyword_static,
184 keyword_struct,
185 keyword_switch,
186 keyword_typedef,
187 keyword_typeof1,
188 keyword_typeof2,
189 keyword_union,
190 keyword_unsigned,
191 keyword_void,
192 keyword_volatile,
193 keyword_while,
194
195 // ISO C99
196 keyword_bool,
197 keyword_complex,
198 keyword_imaginary,
199 keyword_inline,
200 keyword_restrict,
201
202 // ISO C11
203 keyword_alignas,
204 keyword_alignof,
205 keyword_atomic,
206 keyword_generic,
207 keyword_noreturn,
208 keyword_static_assert,
209 keyword_thread_local,
210
211 // ISO C23
212 keyword_bit_int,
213 keyword_c23_alignas,
214 keyword_c23_alignof,
215 keyword_c23_bool,
216 keyword_c23_static_assert,
217 keyword_c23_thread_local,
218 keyword_constexpr,
219 keyword_true,
220 keyword_false,
221 keyword_nullptr,
222 keyword_typeof_unqual,
223
224 // Preprocessor directives
225 keyword_include,
226 keyword_include_next,
227 keyword_embed,
228 keyword_define,
229 keyword_defined,
230 keyword_undef,
231 keyword_ifdef,
232 keyword_ifndef,
233 keyword_elif,
234 keyword_elifdef,
235 keyword_elifndef,
236 keyword_endif,
237 keyword_error,
238 keyword_warning,
239 keyword_pragma,
240 keyword_line,
241 keyword_va_args,
242 keyword_va_opt,
243
244 // gcc keywords
245 keyword_const1,
246 keyword_const2,
247 keyword_inline1,
248 keyword_inline2,
249 keyword_volatile1,
250 keyword_volatile2,
251 keyword_restrict1,
252 keyword_restrict2,
253 keyword_alignof1,
254 keyword_alignof2,
255 keyword_typeof,
256 keyword_attribute1,
257 keyword_attribute2,
258 keyword_extension,
259 keyword_asm,
260 keyword_asm1,
261 keyword_asm2,
262 /// _Float128
263 keyword_float128_1,
264 /// __float128
265 keyword_float128_2,
266 keyword_int128,
267 keyword_imag1,
268 keyword_imag2,
269 keyword_real1,
270 keyword_real2,
271 keyword_float16,
272
273 // clang keywords
274 keyword_fp16,
275
276 // ms keywords
277 keyword_declspec,
278 keyword_int64,
279 keyword_int64_2,
280 keyword_int32,
281 keyword_int32_2,
282 keyword_int16,
283 keyword_int16_2,
284 keyword_int8,
285 keyword_int8_2,
286 keyword_stdcall,
287 keyword_stdcall2,
288 keyword_thiscall,
289 keyword_thiscall2,
290 keyword_vectorcall,
291 keyword_vectorcall2,
292
293 // builtins that require special parsing
294 builtin_choose_expr,
295 builtin_va_arg,
296 builtin_offsetof,
297 builtin_bitoffsetof,
298 builtin_types_compatible_p,
299
300 /// Generated by #embed directive
301 /// Decimal value with no prefix or suffix
302 embed_byte,
303
304 /// preprocessor number
305 /// An optional period, followed by a digit 0-9, followed by any number of letters
306 /// digits, underscores, periods, and exponents (e+, e-, E+, E-, p+, p-, P+, P-)
307 pp_num,
308
309 /// preprocessor placemarker token
310 /// generated if `##` is used with a zero-token argument
311 /// removed after substitution, so the parser should never see this
312 /// See C99 6.10.3.3.2
313 placemarker,
314
315 /// Virtual linemarker token output from preprocessor to indicate start of a new include
316 include_start,
317
318 /// Virtual linemarker token output from preprocessor to indicate resuming a file after
319 /// completion of the preceding #include
320 include_resume,
321
322 /// A comment token if asked to preserve comments.
323 comment,
324
325 /// Return true if token is identifier or keyword.
326 pub fn isMacroIdentifier(id: Id) bool {
327 switch (id) {
328 .keyword_include,
329 .keyword_include_next,
330 .keyword_embed,
331 .keyword_define,
332 .keyword_defined,
333 .keyword_undef,
334 .keyword_ifdef,
335 .keyword_ifndef,
336 .keyword_elif,
337 .keyword_elifdef,
338 .keyword_elifndef,
339 .keyword_endif,
340 .keyword_error,
341 .keyword_warning,
342 .keyword_pragma,
343 .keyword_line,
344 .keyword_va_args,
345 .keyword_va_opt,
346 .macro_func,
347 .macro_function,
348 .macro_pretty_func,
349 .keyword_auto,
350 .keyword_auto_type,
351 .keyword_break,
352 .keyword_case,
353 .keyword_char,
354 .keyword_const,
355 .keyword_continue,
356 .keyword_default,
357 .keyword_do,
358 .keyword_double,
359 .keyword_else,
360 .keyword_enum,
361 .keyword_extern,
362 .keyword_float,
363 .keyword_for,
364 .keyword_goto,
365 .keyword_if,
366 .keyword_int,
367 .keyword_long,
368 .keyword_register,
369 .keyword_return,
370 .keyword_short,
371 .keyword_signed,
372 .keyword_signed1,
373 .keyword_signed2,
374 .keyword_sizeof,
375 .keyword_static,
376 .keyword_struct,
377 .keyword_switch,
378 .keyword_typedef,
379 .keyword_union,
380 .keyword_unsigned,
381 .keyword_void,
382 .keyword_volatile,
383 .keyword_while,
384 .keyword_bool,
385 .keyword_complex,
386 .keyword_imaginary,
387 .keyword_inline,
388 .keyword_restrict,
389 .keyword_alignas,
390 .keyword_alignof,
391 .keyword_atomic,
392 .keyword_generic,
393 .keyword_noreturn,
394 .keyword_static_assert,
395 .keyword_thread_local,
396 .identifier,
397 .extended_identifier,
398 .keyword_typeof,
399 .keyword_typeof1,
400 .keyword_typeof2,
401 .keyword_const1,
402 .keyword_const2,
403 .keyword_inline1,
404 .keyword_inline2,
405 .keyword_volatile1,
406 .keyword_volatile2,
407 .keyword_restrict1,
408 .keyword_restrict2,
409 .keyword_alignof1,
410 .keyword_alignof2,
411 .builtin_choose_expr,
412 .builtin_va_arg,
413 .builtin_offsetof,
414 .builtin_bitoffsetof,
415 .builtin_types_compatible_p,
416 .keyword_attribute1,
417 .keyword_attribute2,
418 .keyword_extension,
419 .keyword_asm,
420 .keyword_asm1,
421 .keyword_asm2,
422 .keyword_float128_1,
423 .keyword_float128_2,
424 .keyword_int128,
425 .keyword_imag1,
426 .keyword_imag2,
427 .keyword_real1,
428 .keyword_real2,
429 .keyword_float16,
430 .keyword_fp16,
431 .keyword_declspec,
432 .keyword_int64,
433 .keyword_int64_2,
434 .keyword_int32,
435 .keyword_int32_2,
436 .keyword_int16,
437 .keyword_int16_2,
438 .keyword_int8,
439 .keyword_int8_2,
440 .keyword_stdcall,
441 .keyword_stdcall2,
442 .keyword_thiscall,
443 .keyword_thiscall2,
444 .keyword_vectorcall,
445 .keyword_vectorcall2,
446 .keyword_bit_int,
447 .keyword_c23_alignas,
448 .keyword_c23_alignof,
449 .keyword_c23_bool,
450 .keyword_c23_static_assert,
451 .keyword_c23_thread_local,
452 .keyword_constexpr,
453 .keyword_true,
454 .keyword_false,
455 .keyword_nullptr,
456 .keyword_typeof_unqual,
457 => return true,
458 else => return false,
459 }
460 }
461
462 /// Turn macro keywords into identifiers.
463 /// `keyword_defined` is special since it should only turn into an identifier if
464 /// we are *not* in an #if or #elif expression
465 pub fn simplifyMacroKeywordExtra(id: *Id, defined_to_identifier: bool) void {
466 switch (id.*) {
467 .keyword_include,
468 .keyword_include_next,
469 .keyword_embed,
470 .keyword_define,
471 .keyword_undef,
472 .keyword_ifdef,
473 .keyword_ifndef,
474 .keyword_elif,
475 .keyword_elifdef,
476 .keyword_elifndef,
477 .keyword_endif,
478 .keyword_error,
479 .keyword_warning,
480 .keyword_pragma,
481 .keyword_line,
482 .keyword_va_args,
483 .keyword_va_opt,
484 => id.* = .identifier,
485 .keyword_defined => if (defined_to_identifier) {
486 id.* = .identifier;
487 },
488 else => {},
489 }
490 }
491
492 pub fn simplifyMacroKeyword(id: *Id) void {
493 simplifyMacroKeywordExtra(id, false);
494 }
495
496 pub fn lexeme(id: Id) ?[]const u8 {
497 return switch (id) {
498 .include_start,
499 .include_resume,
500 => unreachable,
501
502 .unterminated_comment,
503 .invalid,
504 .identifier,
505 .extended_identifier,
506 .string_literal,
507 .string_literal_utf_16,
508 .string_literal_utf_8,
509 .string_literal_utf_32,
510 .string_literal_wide,
511 .unterminated_string_literal,
512 .unterminated_char_literal,
513 .empty_char_literal,
514 .char_literal,
515 .char_literal_utf_8,
516 .char_literal_utf_16,
517 .char_literal_utf_32,
518 .char_literal_wide,
519 .macro_string,
520 .whitespace,
521 .pp_num,
522 .embed_byte,
523 .comment,
524 => null,
525
526 .zero => "0",
527 .one => "1",
528
529 .nl,
530 .eof,
531 .macro_param,
532 .macro_param_no_expand,
533 .stringify_param,
534 .stringify_va_args,
535 .macro_param_has_attribute,
536 .macro_param_has_c_attribute,
537 .macro_param_has_declspec_attribute,
538 .macro_param_has_warning,
539 .macro_param_has_feature,
540 .macro_param_has_extension,
541 .macro_param_has_builtin,
542 .macro_param_has_include,
543 .macro_param_has_include_next,
544 .macro_param_has_embed,
545 .macro_param_is_identifier,
546 .macro_file,
547 .macro_line,
548 .macro_counter,
549 .macro_param_pragma_operator,
550 .placemarker,
551 => "",
552 .macro_ws => " ",
553
554 .macro_func => "__func__",
555 .macro_function => "__FUNCTION__",
556 .macro_pretty_func => "__PRETTY_FUNCTION__",
557
558 .bang => "!",
559 .bang_equal => "!=",
560 .pipe => "|",
561 .pipe_pipe => "||",
562 .pipe_equal => "|=",
563 .equal => "=",
564 .equal_equal => "==",
565 .l_paren => "(",
566 .r_paren => ")",
567 .l_brace => "{",
568 .r_brace => "}",
569 .l_bracket => "[",
570 .r_bracket => "]",
571 .period => ".",
572 .ellipsis => "...",
573 .caret => "^",
574 .caret_equal => "^=",
575 .plus => "+",
576 .plus_plus => "++",
577 .plus_equal => "+=",
578 .minus => "-",
579 .minus_minus => "--",
580 .minus_equal => "-=",
581 .asterisk => "*",
582 .asterisk_equal => "*=",
583 .percent => "%",
584 .percent_equal => "%=",
585 .arrow => "->",
586 .colon => ":",
587 .colon_colon => "::",
588 .semicolon => ";",
589 .slash => "/",
590 .slash_equal => "/=",
591 .comma => ",",
592 .ampersand => "&",
593 .ampersand_ampersand => "&&",
594 .ampersand_equal => "&=",
595 .question_mark => "?",
596 .angle_bracket_left => "<",
597 .angle_bracket_left_equal => "<=",
598 .angle_bracket_angle_bracket_left => "<<",
599 .angle_bracket_angle_bracket_left_equal => "<<=",
600 .angle_bracket_right => ">",
601 .angle_bracket_right_equal => ">=",
602 .angle_bracket_angle_bracket_right => ">>",
603 .angle_bracket_angle_bracket_right_equal => ">>=",
604 .tilde => "~",
605 .hash => "#",
606 .hash_hash => "##",
607
608 .keyword_auto => "auto",
609 .keyword_auto_type => "__auto_type",
610 .keyword_break => "break",
611 .keyword_case => "case",
612 .keyword_char => "char",
613 .keyword_const => "const",
614 .keyword_continue => "continue",
615 .keyword_default => "default",
616 .keyword_do => "do",
617 .keyword_double => "double",
618 .keyword_else => "else",
619 .keyword_enum => "enum",
620 .keyword_extern => "extern",
621 .keyword_float => "float",
622 .keyword_for => "for",
623 .keyword_goto => "goto",
624 .keyword_if => "if",
625 .keyword_int => "int",
626 .keyword_long => "long",
627 .keyword_register => "register",
628 .keyword_return => "return",
629 .keyword_short => "short",
630 .keyword_signed => "signed",
631 .keyword_signed1 => "__signed",
632 .keyword_signed2 => "__signed__",
633 .keyword_sizeof => "sizeof",
634 .keyword_static => "static",
635 .keyword_struct => "struct",
636 .keyword_switch => "switch",
637 .keyword_typedef => "typedef",
638 .keyword_typeof => "typeof",
639 .keyword_union => "union",
640 .keyword_unsigned => "unsigned",
641 .keyword_void => "void",
642 .keyword_volatile => "volatile",
643 .keyword_while => "while",
644 .keyword_bool => "_Bool",
645 .keyword_complex => "_Complex",
646 .keyword_imaginary => "_Imaginary",
647 .keyword_inline => "inline",
648 .keyword_restrict => "restrict",
649 .keyword_alignas => "_Alignas",
650 .keyword_alignof => "_Alignof",
651 .keyword_atomic => "_Atomic",
652 .keyword_generic => "_Generic",
653 .keyword_noreturn => "_Noreturn",
654 .keyword_static_assert => "_Static_assert",
655 .keyword_thread_local => "_Thread_local",
656 .keyword_bit_int => "_BitInt",
657 .keyword_c23_alignas => "alignas",
658 .keyword_c23_alignof => "alignof",
659 .keyword_c23_bool => "bool",
660 .keyword_c23_static_assert => "static_assert",
661 .keyword_c23_thread_local => "thread_local",
662 .keyword_constexpr => "constexpr",
663 .keyword_true => "true",
664 .keyword_false => "false",
665 .keyword_nullptr => "nullptr",
666 .keyword_typeof_unqual => "typeof_unqual",
667 .keyword_include => "include",
668 .keyword_include_next => "include_next",
669 .keyword_embed => "embed",
670 .keyword_define => "define",
671 .keyword_defined => "defined",
672 .keyword_undef => "undef",
673 .keyword_ifdef => "ifdef",
674 .keyword_ifndef => "ifndef",
675 .keyword_elif => "elif",
676 .keyword_elifdef => "elifdef",
677 .keyword_elifndef => "elifndef",
678 .keyword_endif => "endif",
679 .keyword_error => "error",
680 .keyword_warning => "warning",
681 .keyword_pragma => "pragma",
682 .keyword_line => "line",
683 .keyword_va_args => "__VA_ARGS__",
684 .keyword_va_opt => "__VA_OPT__",
685 .keyword_const1 => "__const",
686 .keyword_const2 => "__const__",
687 .keyword_inline1 => "__inline",
688 .keyword_inline2 => "__inline__",
689 .keyword_volatile1 => "__volatile",
690 .keyword_volatile2 => "__volatile__",
691 .keyword_restrict1 => "__restrict",
692 .keyword_restrict2 => "__restrict__",
693 .keyword_alignof1 => "__alignof",
694 .keyword_alignof2 => "__alignof__",
695 .keyword_typeof1 => "__typeof",
696 .keyword_typeof2 => "__typeof__",
697 .builtin_choose_expr => "__builtin_choose_expr",
698 .builtin_va_arg => "__builtin_va_arg",
699 .builtin_offsetof => "__builtin_offsetof",
700 .builtin_bitoffsetof => "__builtin_bitoffsetof",
701 .builtin_types_compatible_p => "__builtin_types_compatible_p",
702 .keyword_attribute1 => "__attribute",
703 .keyword_attribute2 => "__attribute__",
704 .keyword_extension => "__extension__",
705 .keyword_asm => "asm",
706 .keyword_asm1 => "__asm",
707 .keyword_asm2 => "__asm__",
708 .keyword_float128_1 => "_Float128",
709 .keyword_float128_2 => "__float128",
710 .keyword_int128 => "__int128",
711 .keyword_imag1 => "__imag",
712 .keyword_imag2 => "__imag__",
713 .keyword_real1 => "__real",
714 .keyword_real2 => "__real__",
715 .keyword_float16 => "_Float16",
716 .keyword_fp16 => "__fp16",
717 .keyword_declspec => "__declspec",
718 .keyword_int64 => "__int64",
719 .keyword_int64_2 => "_int64",
720 .keyword_int32 => "__int32",
721 .keyword_int32_2 => "_int32",
722 .keyword_int16 => "__int16",
723 .keyword_int16_2 => "_int16",
724 .keyword_int8 => "__int8",
725 .keyword_int8_2 => "_int8",
726 .keyword_stdcall => "__stdcall",
727 .keyword_stdcall2 => "_stdcall",
728 .keyword_thiscall => "__thiscall",
729 .keyword_thiscall2 => "_thiscall",
730 .keyword_vectorcall => "__vectorcall",
731 .keyword_vectorcall2 => "_vectorcall",
732 };
733 }
734
735 pub fn symbol(id: Id) []const u8 {
736 return switch (id) {
737 .macro_string => unreachable,
738 .invalid => "invalid bytes",
739 .identifier,
740 .extended_identifier,
741 .macro_func,
742 .macro_function,
743 .macro_pretty_func,
744 .builtin_choose_expr,
745 .builtin_va_arg,
746 .builtin_offsetof,
747 .builtin_bitoffsetof,
748 .builtin_types_compatible_p,
749 => "an identifier",
750 .string_literal,
751 .string_literal_utf_16,
752 .string_literal_utf_8,
753 .string_literal_utf_32,
754 .string_literal_wide,
755 .unterminated_string_literal,
756 => "a string literal",
757 .char_literal,
758 .char_literal_utf_8,
759 .char_literal_utf_16,
760 .char_literal_utf_32,
761 .char_literal_wide,
762 .unterminated_char_literal,
763 .empty_char_literal,
764 => "a character literal",
765 .pp_num, .embed_byte => "A number",
766 else => id.lexeme().?,
767 };
768 }
769
770 /// tokens that can start an expression parsed by Preprocessor.expr
771 /// Note that eof, r_paren, and string literals cannot actually start a
772 /// preprocessor expression, but we include them here so that a nicer
773 /// error message can be generated by the parser.
774 pub fn validPreprocessorExprStart(id: Id) bool {
775 return switch (id) {
776 .eof,
777 .r_paren,
778 .string_literal,
779 .string_literal_utf_16,
780 .string_literal_utf_8,
781 .string_literal_utf_32,
782 .string_literal_wide,
783
784 .char_literal,
785 .char_literal_utf_8,
786 .char_literal_utf_16,
787 .char_literal_utf_32,
788 .char_literal_wide,
789 .l_paren,
790 .plus,
791 .minus,
792 .tilde,
793 .bang,
794 .identifier,
795 .extended_identifier,
796 .keyword_defined,
797 .one,
798 .zero,
799 .pp_num,
800 .keyword_true,
801 .keyword_false,
802 => true,
803 else => false,
804 };
805 }
806
807 pub fn allowsDigraphs(id: Id, langopts: LangOpts) bool {
808 return switch (id) {
809 .l_bracket,
810 .r_bracket,
811 .l_brace,
812 .r_brace,
813 .hash,
814 .hash_hash,
815 => langopts.hasDigraphs(),
816 else => false,
817 };
818 }
819
820 pub fn canOpenGCCAsmStmt(id: Id) bool {
821 return switch (id) {
822 .keyword_volatile, .keyword_volatile1, .keyword_volatile2, .keyword_inline, .keyword_inline1, .keyword_inline2, .keyword_goto, .l_paren => true,
823 else => false,
824 };
825 }
826
827 pub fn isStringLiteral(id: Id) bool {
828 return switch (id) {
829 .string_literal, .string_literal_utf_16, .string_literal_utf_8, .string_literal_utf_32, .string_literal_wide => true,
830 else => false,
831 };
832 }
833 };
834
835 /// double underscore and underscore + capital letter identifiers
836 /// belong to the implementation namespace, so we always convert them
837 /// to keywords.
838 pub fn getTokenId(langopts: LangOpts, str: []const u8) Token.Id {
839 const kw = all_kws.get(str) orelse return .identifier;
840 const standard = langopts.standard;
841 return switch (kw) {
842 .keyword_inline => if (standard.isGNU() or standard.atLeast(.c99)) kw else .identifier,
843 .keyword_restrict => if (standard.atLeast(.c99)) kw else .identifier,
844 .keyword_typeof => if (standard.isGNU() or standard.atLeast(.c23)) kw else .identifier,
845 .keyword_asm => if (standard.isGNU()) kw else .identifier,
846 .keyword_declspec => if (langopts.declspec_attrs) kw else .identifier,
847
848 .keyword_c23_alignas,
849 .keyword_c23_alignof,
850 .keyword_c23_bool,
851 .keyword_c23_static_assert,
852 .keyword_c23_thread_local,
853 .keyword_constexpr,
854 .keyword_true,
855 .keyword_false,
856 .keyword_nullptr,
857 .keyword_typeof_unqual,
858 .keyword_elifdef,
859 .keyword_elifndef,
860 => if (standard.atLeast(.c23)) kw else .identifier,
861
862 .keyword_int64,
863 .keyword_int64_2,
864 .keyword_int32,
865 .keyword_int32_2,
866 .keyword_int16,
867 .keyword_int16_2,
868 .keyword_int8,
869 .keyword_int8_2,
870 .keyword_stdcall2,
871 .keyword_thiscall2,
872 .keyword_vectorcall2,
873 => if (langopts.ms_extensions) kw else .identifier,
874 else => kw,
875 };
876 }
877
878 const all_kws = std.StaticStringMap(Id).initComptime(.{
879 .{ "auto", .keyword_auto },
880 .{ "break", .keyword_break },
881 .{ "case", .keyword_case },
882 .{ "char", .keyword_char },
883 .{ "const", .keyword_const },
884 .{ "continue", .keyword_continue },
885 .{ "default", .keyword_default },
886 .{ "do", .keyword_do },
887 .{ "double", .keyword_double },
888 .{ "else", .keyword_else },
889 .{ "enum", .keyword_enum },
890 .{ "extern", .keyword_extern },
891 .{ "float", .keyword_float },
892 .{ "for", .keyword_for },
893 .{ "goto", .keyword_goto },
894 .{ "if", .keyword_if },
895 .{ "int", .keyword_int },
896 .{ "long", .keyword_long },
897 .{ "register", .keyword_register },
898 .{ "return", .keyword_return },
899 .{ "short", .keyword_short },
900 .{ "signed", .keyword_signed },
901 .{ "__signed", .keyword_signed1 },
902 .{ "__signed__", .keyword_signed2 },
903 .{ "sizeof", .keyword_sizeof },
904 .{ "static", .keyword_static },
905 .{ "struct", .keyword_struct },
906 .{ "switch", .keyword_switch },
907 .{ "typedef", .keyword_typedef },
908 .{ "union", .keyword_union },
909 .{ "unsigned", .keyword_unsigned },
910 .{ "void", .keyword_void },
911 .{ "volatile", .keyword_volatile },
912 .{ "while", .keyword_while },
913 .{ "__typeof__", .keyword_typeof2 },
914 .{ "__typeof", .keyword_typeof1 },
915
916 // ISO C99
917 .{ "_Bool", .keyword_bool },
918 .{ "_Complex", .keyword_complex },
919 .{ "_Imaginary", .keyword_imaginary },
920 .{ "inline", .keyword_inline },
921 .{ "restrict", .keyword_restrict },
922
923 // ISO C11
924 .{ "_Alignas", .keyword_alignas },
925 .{ "_Alignof", .keyword_alignof },
926 .{ "_Atomic", .keyword_atomic },
927 .{ "_Generic", .keyword_generic },
928 .{ "_Noreturn", .keyword_noreturn },
929 .{ "_Static_assert", .keyword_static_assert },
930 .{ "_Thread_local", .keyword_thread_local },
931
932 // ISO C23
933 .{ "_BitInt", .keyword_bit_int },
934 .{ "alignas", .keyword_c23_alignas },
935 .{ "alignof", .keyword_c23_alignof },
936 .{ "bool", .keyword_c23_bool },
937 .{ "static_assert", .keyword_c23_static_assert },
938 .{ "thread_local", .keyword_c23_thread_local },
939 .{ "constexpr", .keyword_constexpr },
940 .{ "true", .keyword_true },
941 .{ "false", .keyword_false },
942 .{ "nullptr", .keyword_nullptr },
943 .{ "typeof_unqual", .keyword_typeof_unqual },
944
945 // Preprocessor directives
946 .{ "include", .keyword_include },
947 .{ "include_next", .keyword_include_next },
948 .{ "embed", .keyword_embed },
949 .{ "define", .keyword_define },
950 .{ "defined", .keyword_defined },
951 .{ "undef", .keyword_undef },
952 .{ "ifdef", .keyword_ifdef },
953 .{ "ifndef", .keyword_ifndef },
954 .{ "elif", .keyword_elif },
955 .{ "elifdef", .keyword_elifdef },
956 .{ "elifndef", .keyword_elifndef },
957 .{ "endif", .keyword_endif },
958 .{ "error", .keyword_error },
959 .{ "warning", .keyword_warning },
960 .{ "pragma", .keyword_pragma },
961 .{ "line", .keyword_line },
962 .{ "__VA_ARGS__", .keyword_va_args },
963 .{ "__VA_OPT__", .keyword_va_opt },
964 .{ "__func__", .macro_func },
965 .{ "__FUNCTION__", .macro_function },
966 .{ "__PRETTY_FUNCTION__", .macro_pretty_func },
967
968 // gcc keywords
969 .{ "__auto_type", .keyword_auto_type },
970 .{ "__const", .keyword_const1 },
971 .{ "__const__", .keyword_const2 },
972 .{ "__inline", .keyword_inline1 },
973 .{ "__inline__", .keyword_inline2 },
974 .{ "__volatile", .keyword_volatile1 },
975 .{ "__volatile__", .keyword_volatile2 },
976 .{ "__restrict", .keyword_restrict1 },
977 .{ "__restrict__", .keyword_restrict2 },
978 .{ "__alignof", .keyword_alignof1 },
979 .{ "__alignof__", .keyword_alignof2 },
980 .{ "typeof", .keyword_typeof },
981 .{ "__attribute", .keyword_attribute1 },
982 .{ "__attribute__", .keyword_attribute2 },
983 .{ "__extension__", .keyword_extension },
984 .{ "asm", .keyword_asm },
985 .{ "__asm", .keyword_asm1 },
986 .{ "__asm__", .keyword_asm2 },
987 .{ "_Float128", .keyword_float128_1 },
988 .{ "__float128", .keyword_float128_2 },
989 .{ "__int128", .keyword_int128 },
990 .{ "__imag", .keyword_imag1 },
991 .{ "__imag__", .keyword_imag2 },
992 .{ "__real", .keyword_real1 },
993 .{ "__real__", .keyword_real2 },
994 .{ "_Float16", .keyword_float16 },
995
996 // clang keywords
997 .{ "__fp16", .keyword_fp16 },
998
999 // ms keywords
1000 .{ "__declspec", .keyword_declspec },
1001 .{ "__int64", .keyword_int64 },
1002 .{ "_int64", .keyword_int64_2 },
1003 .{ "__int32", .keyword_int32 },
1004 .{ "_int32", .keyword_int32_2 },
1005 .{ "__int16", .keyword_int16 },
1006 .{ "_int16", .keyword_int16_2 },
1007 .{ "__int8", .keyword_int8 },
1008 .{ "_int8", .keyword_int8_2 },
1009 .{ "__stdcall", .keyword_stdcall },
1010 .{ "_stdcall", .keyword_stdcall2 },
1011 .{ "__thiscall", .keyword_thiscall },
1012 .{ "_thiscall", .keyword_thiscall2 },
1013 .{ "__vectorcall", .keyword_vectorcall },
1014 .{ "_vectorcall", .keyword_vectorcall2 },
1015
1016 // builtins that require special parsing
1017 .{ "__builtin_choose_expr", .builtin_choose_expr },
1018 .{ "__builtin_va_arg", .builtin_va_arg },
1019 .{ "__builtin_offsetof", .builtin_offsetof },
1020 .{ "__builtin_bitoffsetof", .builtin_bitoffsetof },
1021 .{ "__builtin_types_compatible_p", .builtin_types_compatible_p },
1022 });
1023};
1024
1025const Tokenizer = @This();
1026
1027buf: []const u8,
1028index: u32 = 0,
1029source: Source.Id,
1030langopts: LangOpts,
1031line: u32 = 1,
1032
1033pub fn next(self: *Tokenizer) Token {
1034 var state: enum {
1035 start,
1036 whitespace,
1037 u,
1038 u8,
1039 U,
1040 L,
1041 string_literal,
1042 char_literal_start,
1043 char_literal,
1044 char_escape_sequence,
1045 string_escape_sequence,
1046 identifier,
1047 extended_identifier,
1048 equal,
1049 bang,
1050 pipe,
1051 colon,
1052 percent,
1053 asterisk,
1054 plus,
1055 angle_bracket_left,
1056 angle_bracket_angle_bracket_left,
1057 angle_bracket_right,
1058 angle_bracket_angle_bracket_right,
1059 caret,
1060 period,
1061 period2,
1062 minus,
1063 slash,
1064 ampersand,
1065 hash,
1066 hash_digraph,
1067 hash_hash_digraph_partial,
1068 line_comment,
1069 multi_line_comment,
1070 multi_line_comment_asterisk,
1071 multi_line_comment_done,
1072 pp_num,
1073 pp_num_exponent,
1074 pp_num_digit_separator,
1075 } = .start;
1076
1077 var start = self.index;
1078 var id: Token.Id = .eof;
1079
1080 while (self.index < self.buf.len) : (self.index += 1) {
1081 const c = self.buf[self.index];
1082 switch (state) {
1083 .start => switch (c) {
1084 '\n' => {
1085 id = .nl;
1086 self.index += 1;
1087 self.line += 1;
1088 break;
1089 },
1090 '"' => {
1091 id = .string_literal;
1092 state = .string_literal;
1093 },
1094 '\'' => {
1095 id = .char_literal;
1096 state = .char_literal_start;
1097 },
1098 'u' => state = .u,
1099 'U' => state = .U,
1100 'L' => state = .L,
1101 'a'...'t', 'v'...'z', 'A'...'K', 'M'...'T', 'V'...'Z', '_' => state = .identifier,
1102 '=' => state = .equal,
1103 '!' => state = .bang,
1104 '|' => state = .pipe,
1105 '(' => {
1106 id = .l_paren;
1107 self.index += 1;
1108 break;
1109 },
1110 ')' => {
1111 id = .r_paren;
1112 self.index += 1;
1113 break;
1114 },
1115 '[' => {
1116 id = .l_bracket;
1117 self.index += 1;
1118 break;
1119 },
1120 ']' => {
1121 id = .r_bracket;
1122 self.index += 1;
1123 break;
1124 },
1125 ';' => {
1126 id = .semicolon;
1127 self.index += 1;
1128 break;
1129 },
1130 ',' => {
1131 id = .comma;
1132 self.index += 1;
1133 break;
1134 },
1135 '?' => {
1136 id = .question_mark;
1137 self.index += 1;
1138 break;
1139 },
1140 ':' => state = .colon,
1141 '%' => state = .percent,
1142 '*' => state = .asterisk,
1143 '+' => state = .plus,
1144 '<' => state = .angle_bracket_left,
1145 '>' => state = .angle_bracket_right,
1146 '^' => state = .caret,
1147 '{' => {
1148 id = .l_brace;
1149 self.index += 1;
1150 break;
1151 },
1152 '}' => {
1153 id = .r_brace;
1154 self.index += 1;
1155 break;
1156 },
1157 '~' => {
1158 id = .tilde;
1159 self.index += 1;
1160 break;
1161 },
1162 '.' => state = .period,
1163 '-' => state = .minus,
1164 '/' => state = .slash,
1165 '&' => state = .ampersand,
1166 '#' => state = .hash,
1167 '0'...'9' => state = .pp_num,
1168 '\t', '\x0B', '\x0C', ' ' => state = .whitespace,
1169 '$' => if (self.langopts.dollars_in_identifiers) {
1170 state = .extended_identifier;
1171 } else {
1172 id = .invalid;
1173 self.index += 1;
1174 break;
1175 },
1176 0x1A => if (self.langopts.ms_extensions) {
1177 id = .eof;
1178 break;
1179 } else {
1180 id = .invalid;
1181 self.index += 1;
1182 break;
1183 },
1184 0x80...0xFF => state = .extended_identifier,
1185 else => {
1186 id = .invalid;
1187 self.index += 1;
1188 break;
1189 },
1190 },
1191 .whitespace => switch (c) {
1192 '\t', '\x0B', '\x0C', ' ' => {},
1193 else => {
1194 id = .whitespace;
1195 break;
1196 },
1197 },
1198 .u => switch (c) {
1199 '8' => {
1200 state = .u8;
1201 },
1202 '\'' => {
1203 id = .char_literal_utf_16;
1204 state = .char_literal_start;
1205 },
1206 '\"' => {
1207 id = .string_literal_utf_16;
1208 state = .string_literal;
1209 },
1210 else => {
1211 self.index -= 1;
1212 state = .identifier;
1213 },
1214 },
1215 .u8 => switch (c) {
1216 '\"' => {
1217 id = .string_literal_utf_8;
1218 state = .string_literal;
1219 },
1220 '\'' => {
1221 id = .char_literal_utf_8;
1222 state = .char_literal_start;
1223 },
1224 else => {
1225 self.index -= 1;
1226 state = .identifier;
1227 },
1228 },
1229 .U => switch (c) {
1230 '\'' => {
1231 id = .char_literal_utf_32;
1232 state = .char_literal_start;
1233 },
1234 '\"' => {
1235 id = .string_literal_utf_32;
1236 state = .string_literal;
1237 },
1238 else => {
1239 self.index -= 1;
1240 state = .identifier;
1241 },
1242 },
1243 .L => switch (c) {
1244 '\'' => {
1245 id = .char_literal_wide;
1246 state = .char_literal_start;
1247 },
1248 '\"' => {
1249 id = .string_literal_wide;
1250 state = .string_literal;
1251 },
1252 else => {
1253 self.index -= 1;
1254 state = .identifier;
1255 },
1256 },
1257 .string_literal => switch (c) {
1258 '\\' => {
1259 state = .string_escape_sequence;
1260 },
1261 '"' => {
1262 self.index += 1;
1263 break;
1264 },
1265 '\n' => {
1266 id = .unterminated_string_literal;
1267 break;
1268 },
1269 '\r' => unreachable,
1270 else => {},
1271 },
1272 .char_literal_start => switch (c) {
1273 '\\' => {
1274 state = .char_escape_sequence;
1275 },
1276 '\'' => {
1277 id = .empty_char_literal;
1278 self.index += 1;
1279 break;
1280 },
1281 '\n' => {
1282 id = .unterminated_char_literal;
1283 break;
1284 },
1285 else => {
1286 state = .char_literal;
1287 },
1288 },
1289 .char_literal => switch (c) {
1290 '\\' => {
1291 state = .char_escape_sequence;
1292 },
1293 '\'' => {
1294 self.index += 1;
1295 break;
1296 },
1297 '\n' => {
1298 id = .unterminated_char_literal;
1299 break;
1300 },
1301 else => {},
1302 },
1303 .char_escape_sequence => switch (c) {
1304 '\r', '\n' => {
1305 id = .unterminated_char_literal;
1306 break;
1307 },
1308 else => state = .char_literal,
1309 },
1310 .string_escape_sequence => switch (c) {
1311 '\r', '\n' => {
1312 id = .unterminated_string_literal;
1313 break;
1314 },
1315 else => state = .string_literal,
1316 },
1317 .identifier, .extended_identifier => switch (c) {
1318 'a'...'z', 'A'...'Z', '_', '0'...'9' => {},
1319 '$' => if (self.langopts.dollars_in_identifiers) {
1320 state = .extended_identifier;
1321 } else {
1322 id = if (state == .identifier) Token.getTokenId(self.langopts, self.buf[start..self.index]) else .extended_identifier;
1323 break;
1324 },
1325 0x80...0xFF => state = .extended_identifier,
1326 else => {
1327 id = if (state == .identifier) Token.getTokenId(self.langopts, self.buf[start..self.index]) else .extended_identifier;
1328 break;
1329 },
1330 },
1331 .equal => switch (c) {
1332 '=' => {
1333 id = .equal_equal;
1334 self.index += 1;
1335 break;
1336 },
1337 else => {
1338 id = .equal;
1339 break;
1340 },
1341 },
1342 .bang => switch (c) {
1343 '=' => {
1344 id = .bang_equal;
1345 self.index += 1;
1346 break;
1347 },
1348 else => {
1349 id = .bang;
1350 break;
1351 },
1352 },
1353 .pipe => switch (c) {
1354 '=' => {
1355 id = .pipe_equal;
1356 self.index += 1;
1357 break;
1358 },
1359 '|' => {
1360 id = .pipe_pipe;
1361 self.index += 1;
1362 break;
1363 },
1364 else => {
1365 id = .pipe;
1366 break;
1367 },
1368 },
1369 .colon => switch (c) {
1370 '>' => {
1371 if (self.langopts.hasDigraphs()) {
1372 id = .r_bracket;
1373 self.index += 1;
1374 } else {
1375 id = .colon;
1376 }
1377 break;
1378 },
1379 ':' => {
1380 if (self.langopts.standard.atLeast(.c23)) {
1381 id = .colon_colon;
1382 self.index += 1;
1383 break;
1384 } else {
1385 id = .colon;
1386 break;
1387 }
1388 },
1389 else => {
1390 id = .colon;
1391 break;
1392 },
1393 },
1394 .percent => switch (c) {
1395 '=' => {
1396 id = .percent_equal;
1397 self.index += 1;
1398 break;
1399 },
1400 '>' => {
1401 if (self.langopts.hasDigraphs()) {
1402 id = .r_brace;
1403 self.index += 1;
1404 } else {
1405 id = .percent;
1406 }
1407 break;
1408 },
1409 ':' => {
1410 if (self.langopts.hasDigraphs()) {
1411 state = .hash_digraph;
1412 } else {
1413 id = .percent;
1414 break;
1415 }
1416 },
1417 else => {
1418 id = .percent;
1419 break;
1420 },
1421 },
1422 .asterisk => switch (c) {
1423 '=' => {
1424 id = .asterisk_equal;
1425 self.index += 1;
1426 break;
1427 },
1428 else => {
1429 id = .asterisk;
1430 break;
1431 },
1432 },
1433 .plus => switch (c) {
1434 '=' => {
1435 id = .plus_equal;
1436 self.index += 1;
1437 break;
1438 },
1439 '+' => {
1440 id = .plus_plus;
1441 self.index += 1;
1442 break;
1443 },
1444 else => {
1445 id = .plus;
1446 break;
1447 },
1448 },
1449 .angle_bracket_left => switch (c) {
1450 '<' => state = .angle_bracket_angle_bracket_left,
1451 '=' => {
1452 id = .angle_bracket_left_equal;
1453 self.index += 1;
1454 break;
1455 },
1456 ':' => {
1457 if (self.langopts.hasDigraphs()) {
1458 id = .l_bracket;
1459 self.index += 1;
1460 } else {
1461 id = .angle_bracket_left;
1462 }
1463 break;
1464 },
1465 '%' => {
1466 if (self.langopts.hasDigraphs()) {
1467 id = .l_brace;
1468 self.index += 1;
1469 } else {
1470 id = .angle_bracket_left;
1471 }
1472 break;
1473 },
1474 else => {
1475 id = .angle_bracket_left;
1476 break;
1477 },
1478 },
1479 .angle_bracket_angle_bracket_left => switch (c) {
1480 '=' => {
1481 id = .angle_bracket_angle_bracket_left_equal;
1482 self.index += 1;
1483 break;
1484 },
1485 else => {
1486 id = .angle_bracket_angle_bracket_left;
1487 break;
1488 },
1489 },
1490 .angle_bracket_right => switch (c) {
1491 '>' => state = .angle_bracket_angle_bracket_right,
1492 '=' => {
1493 id = .angle_bracket_right_equal;
1494 self.index += 1;
1495 break;
1496 },
1497 else => {
1498 id = .angle_bracket_right;
1499 break;
1500 },
1501 },
1502 .angle_bracket_angle_bracket_right => switch (c) {
1503 '=' => {
1504 id = .angle_bracket_angle_bracket_right_equal;
1505 self.index += 1;
1506 break;
1507 },
1508 else => {
1509 id = .angle_bracket_angle_bracket_right;
1510 break;
1511 },
1512 },
1513 .caret => switch (c) {
1514 '=' => {
1515 id = .caret_equal;
1516 self.index += 1;
1517 break;
1518 },
1519 else => {
1520 id = .caret;
1521 break;
1522 },
1523 },
1524 .period => switch (c) {
1525 '.' => state = .period2,
1526 '0'...'9' => state = .pp_num,
1527 else => {
1528 id = .period;
1529 break;
1530 },
1531 },
1532 .period2 => switch (c) {
1533 '.' => {
1534 id = .ellipsis;
1535 self.index += 1;
1536 break;
1537 },
1538 else => {
1539 id = .period;
1540 self.index -= 1;
1541 break;
1542 },
1543 },
1544 .minus => switch (c) {
1545 '>' => {
1546 id = .arrow;
1547 self.index += 1;
1548 break;
1549 },
1550 '=' => {
1551 id = .minus_equal;
1552 self.index += 1;
1553 break;
1554 },
1555 '-' => {
1556 id = .minus_minus;
1557 self.index += 1;
1558 break;
1559 },
1560 else => {
1561 id = .minus;
1562 break;
1563 },
1564 },
1565 .ampersand => switch (c) {
1566 '&' => {
1567 id = .ampersand_ampersand;
1568 self.index += 1;
1569 break;
1570 },
1571 '=' => {
1572 id = .ampersand_equal;
1573 self.index += 1;
1574 break;
1575 },
1576 else => {
1577 id = .ampersand;
1578 break;
1579 },
1580 },
1581 .hash => switch (c) {
1582 '#' => {
1583 id = .hash_hash;
1584 self.index += 1;
1585 break;
1586 },
1587 else => {
1588 id = .hash;
1589 break;
1590 },
1591 },
1592 .hash_digraph => switch (c) {
1593 '%' => state = .hash_hash_digraph_partial,
1594 else => {
1595 id = .hash;
1596 break;
1597 },
1598 },
1599 .hash_hash_digraph_partial => switch (c) {
1600 ':' => {
1601 id = .hash_hash;
1602 self.index += 1;
1603 break;
1604 },
1605 else => {
1606 id = .hash;
1607 self.index -= 1; // re-tokenize the percent
1608 break;
1609 },
1610 },
1611 .slash => switch (c) {
1612 '/' => state = .line_comment,
1613 '*' => state = .multi_line_comment,
1614 '=' => {
1615 id = .slash_equal;
1616 self.index += 1;
1617 break;
1618 },
1619 else => {
1620 id = .slash;
1621 break;
1622 },
1623 },
1624 .line_comment => switch (c) {
1625 '\n' => {
1626 if (self.langopts.preserve_comments) {
1627 id = .comment;
1628 break;
1629 }
1630 self.index -= 1;
1631 state = .start;
1632 },
1633 else => {},
1634 },
1635 .multi_line_comment => switch (c) {
1636 '*' => state = .multi_line_comment_asterisk,
1637 '\n' => self.line += 1,
1638 else => {},
1639 },
1640 .multi_line_comment_asterisk => switch (c) {
1641 '/' => {
1642 if (self.langopts.preserve_comments) {
1643 self.index += 1;
1644 id = .comment;
1645 break;
1646 }
1647 state = .multi_line_comment_done;
1648 },
1649 '\n' => {
1650 self.line += 1;
1651 state = .multi_line_comment;
1652 },
1653 '*' => {},
1654 else => state = .multi_line_comment,
1655 },
1656 .multi_line_comment_done => switch (c) {
1657 '\n' => {
1658 start = self.index;
1659 id = .nl;
1660 self.index += 1;
1661 self.line += 1;
1662 break;
1663 },
1664 '\r' => unreachable,
1665 '\t', '\x0B', '\x0C', ' ' => {
1666 start = self.index;
1667 state = .whitespace;
1668 },
1669 else => {
1670 id = .whitespace;
1671 break;
1672 },
1673 },
1674 .pp_num => switch (c) {
1675 'a'...'d',
1676 'A'...'D',
1677 'f'...'o',
1678 'F'...'O',
1679 'q'...'z',
1680 'Q'...'Z',
1681 '0'...'9',
1682 '_',
1683 '.',
1684 => {},
1685 'e', 'E', 'p', 'P' => state = .pp_num_exponent,
1686 '\'' => if (self.langopts.standard.atLeast(.c23)) {
1687 state = .pp_num_digit_separator;
1688 } else {
1689 id = .pp_num;
1690 break;
1691 },
1692 else => {
1693 id = .pp_num;
1694 break;
1695 },
1696 },
1697 .pp_num_digit_separator => switch (c) {
1698 'a'...'d',
1699 'A'...'D',
1700 'f'...'o',
1701 'F'...'O',
1702 'q'...'z',
1703 'Q'...'Z',
1704 '0'...'9',
1705 '_',
1706 => state = .pp_num,
1707 else => {
1708 self.index -= 1;
1709 id = .pp_num;
1710 break;
1711 },
1712 },
1713 .pp_num_exponent => switch (c) {
1714 'a'...'o',
1715 'q'...'z',
1716 'A'...'O',
1717 'Q'...'Z',
1718 '0'...'9',
1719 '_',
1720 '.',
1721 '+',
1722 '-',
1723 => state = .pp_num,
1724 'p', 'P' => {},
1725 else => {
1726 id = .pp_num;
1727 break;
1728 },
1729 },
1730 }
1731 } else if (self.index == self.buf.len) {
1732 switch (state) {
1733 .start, .line_comment => {},
1734 .u, .u8, .U, .L, .identifier => id = Token.getTokenId(self.langopts, self.buf[start..self.index]),
1735 .extended_identifier => id = .extended_identifier,
1736
1737 .period2 => {
1738 self.index -= 1;
1739 id = .period;
1740 },
1741
1742 .multi_line_comment,
1743 .multi_line_comment_asterisk,
1744 => id = .unterminated_comment,
1745
1746 .char_escape_sequence, .char_literal, .char_literal_start => id = .unterminated_char_literal,
1747 .string_escape_sequence, .string_literal => id = .unterminated_string_literal,
1748
1749 .whitespace => id = .whitespace,
1750 .multi_line_comment_done => id = .whitespace,
1751
1752 .equal => id = .equal,
1753 .bang => id = .bang,
1754 .minus => id = .minus,
1755 .slash => id = .slash,
1756 .ampersand => id = .ampersand,
1757 .hash => id = .hash,
1758 .period => id = .period,
1759 .pipe => id = .pipe,
1760 .angle_bracket_angle_bracket_right => id = .angle_bracket_angle_bracket_right,
1761 .angle_bracket_right => id = .angle_bracket_right,
1762 .angle_bracket_angle_bracket_left => id = .angle_bracket_angle_bracket_left,
1763 .angle_bracket_left => id = .angle_bracket_left,
1764 .plus => id = .plus,
1765 .colon => id = .colon,
1766 .percent => id = .percent,
1767 .caret => id = .caret,
1768 .asterisk => id = .asterisk,
1769 .hash_digraph => id = .hash,
1770 .hash_hash_digraph_partial => {
1771 id = .hash;
1772 self.index -= 1; // re-tokenize the percent
1773 },
1774 .pp_num, .pp_num_exponent, .pp_num_digit_separator => id = .pp_num,
1775 }
1776 }
1777
1778 return .{
1779 .id = id,
1780 .start = start,
1781 .end = self.index,
1782 .line = self.line,
1783 .source = self.source,
1784 };
1785}
1786
1787pub fn nextNoWS(self: *Tokenizer) Token {
1788 var tok = self.next();
1789 while (tok.id == .whitespace or tok.id == .comment) tok = self.next();
1790 return tok;
1791}
1792
1793pub fn nextNoWSComments(self: *Tokenizer) Token {
1794 var tok = self.next();
1795 while (tok.id == .whitespace) tok = self.next();
1796 return tok;
1797}
1798
1799/// Try to tokenize a '::' even if not supported by the current language standard.
1800pub fn colonColon(self: *Tokenizer) Token {
1801 var tok = self.nextNoWS();
1802 if (tok.id == .colon and self.index < self.buf.len and self.buf[self.index] == ':') {
1803 self.index += 1;
1804 tok.id = .colon_colon;
1805 }
1806 return tok;
1807}
src/translate_c/aro.zig created+589
...@@ -0,0 +1,589 @@
1const std = @import("std");
2const mem = std.mem;
3const assert = std.debug.assert;
4const Tokenizer = @import("Tokenizer.zig");
5const CToken = Tokenizer.Token;
6const ast = @import("ast.zig");
7const ZigNode = ast.Node;
8
9pub const PatternList = struct {
10 patterns: []Pattern,
11
12 /// Templates must be function-like macros
13 /// first element is macro source, second element is the name of the function
14 /// in std.lib.zig.c_translation.Macros which implements it
15 const templates = [_][2][]const u8{
16 [2][]const u8{ "f_SUFFIX(X) (X ## f)", "F_SUFFIX" },
17 [2][]const u8{ "F_SUFFIX(X) (X ## F)", "F_SUFFIX" },
18
19 [2][]const u8{ "u_SUFFIX(X) (X ## u)", "U_SUFFIX" },
20 [2][]const u8{ "U_SUFFIX(X) (X ## U)", "U_SUFFIX" },
21
22 [2][]const u8{ "l_SUFFIX(X) (X ## l)", "L_SUFFIX" },
23 [2][]const u8{ "L_SUFFIX(X) (X ## L)", "L_SUFFIX" },
24
25 [2][]const u8{ "ul_SUFFIX(X) (X ## ul)", "UL_SUFFIX" },
26 [2][]const u8{ "uL_SUFFIX(X) (X ## uL)", "UL_SUFFIX" },
27 [2][]const u8{ "Ul_SUFFIX(X) (X ## Ul)", "UL_SUFFIX" },
28 [2][]const u8{ "UL_SUFFIX(X) (X ## UL)", "UL_SUFFIX" },
29
30 [2][]const u8{ "ll_SUFFIX(X) (X ## ll)", "LL_SUFFIX" },
31 [2][]const u8{ "LL_SUFFIX(X) (X ## LL)", "LL_SUFFIX" },
32
33 [2][]const u8{ "ull_SUFFIX(X) (X ## ull)", "ULL_SUFFIX" },
34 [2][]const u8{ "uLL_SUFFIX(X) (X ## uLL)", "ULL_SUFFIX" },
35 [2][]const u8{ "Ull_SUFFIX(X) (X ## Ull)", "ULL_SUFFIX" },
36 [2][]const u8{ "ULL_SUFFIX(X) (X ## ULL)", "ULL_SUFFIX" },
37
38 [2][]const u8{ "f_SUFFIX(X) X ## f", "F_SUFFIX" },
39 [2][]const u8{ "F_SUFFIX(X) X ## F", "F_SUFFIX" },
40
41 [2][]const u8{ "u_SUFFIX(X) X ## u", "U_SUFFIX" },
42 [2][]const u8{ "U_SUFFIX(X) X ## U", "U_SUFFIX" },
43
44 [2][]const u8{ "l_SUFFIX(X) X ## l", "L_SUFFIX" },
45 [2][]const u8{ "L_SUFFIX(X) X ## L", "L_SUFFIX" },
46
47 [2][]const u8{ "ul_SUFFIX(X) X ## ul", "UL_SUFFIX" },
48 [2][]const u8{ "uL_SUFFIX(X) X ## uL", "UL_SUFFIX" },
49 [2][]const u8{ "Ul_SUFFIX(X) X ## Ul", "UL_SUFFIX" },
50 [2][]const u8{ "UL_SUFFIX(X) X ## UL", "UL_SUFFIX" },
51
52 [2][]const u8{ "ll_SUFFIX(X) X ## ll", "LL_SUFFIX" },
53 [2][]const u8{ "LL_SUFFIX(X) X ## LL", "LL_SUFFIX" },
54
55 [2][]const u8{ "ull_SUFFIX(X) X ## ull", "ULL_SUFFIX" },
56 [2][]const u8{ "uLL_SUFFIX(X) X ## uLL", "ULL_SUFFIX" },
57 [2][]const u8{ "Ull_SUFFIX(X) X ## Ull", "ULL_SUFFIX" },
58 [2][]const u8{ "ULL_SUFFIX(X) X ## ULL", "ULL_SUFFIX" },
59
60 [2][]const u8{ "CAST_OR_CALL(X, Y) (X)(Y)", "CAST_OR_CALL" },
61 [2][]const u8{ "CAST_OR_CALL(X, Y) ((X)(Y))", "CAST_OR_CALL" },
62
63 [2][]const u8{
64 \\wl_container_of(ptr, sample, member) \
65 \\(__typeof__(sample))((char *)(ptr) - \
66 \\ offsetof(__typeof__(*sample), member))
67 ,
68 "WL_CONTAINER_OF",
69 },
70
71 [2][]const u8{ "IGNORE_ME(X) ((void)(X))", "DISCARD" },
72 [2][]const u8{ "IGNORE_ME(X) (void)(X)", "DISCARD" },
73 [2][]const u8{ "IGNORE_ME(X) ((const void)(X))", "DISCARD" },
74 [2][]const u8{ "IGNORE_ME(X) (const void)(X)", "DISCARD" },
75 [2][]const u8{ "IGNORE_ME(X) ((volatile void)(X))", "DISCARD" },
76 [2][]const u8{ "IGNORE_ME(X) (volatile void)(X)", "DISCARD" },
77 [2][]const u8{ "IGNORE_ME(X) ((const volatile void)(X))", "DISCARD" },
78 [2][]const u8{ "IGNORE_ME(X) (const volatile void)(X)", "DISCARD" },
79 [2][]const u8{ "IGNORE_ME(X) ((volatile const void)(X))", "DISCARD" },
80 [2][]const u8{ "IGNORE_ME(X) (volatile const void)(X)", "DISCARD" },
81 };
82
83 /// Assumes that `ms` represents a tokenized function-like macro.
84 fn buildArgsHash(allocator: mem.Allocator, ms: MacroSlicer, hash: *ArgsPositionMap) MacroProcessingError!void {
85 assert(ms.tokens.len > 2);
86 assert(ms.tokens[0].id == .identifier or ms.tokens[0].id == .extended_identifier);
87 assert(ms.tokens[1].id == .l_paren);
88
89 var i: usize = 2;
90 while (true) : (i += 1) {
91 const token = ms.tokens[i];
92 switch (token.id) {
93 .r_paren => break,
94 .comma => continue,
95 .identifier, .extended_identifier => {
96 const identifier = ms.slice(token);
97 try hash.put(allocator, identifier, i);
98 },
99 else => return error.UnexpectedMacroToken,
100 }
101 }
102 }
103
104 const Pattern = struct {
105 tokens: []const CToken,
106 source: []const u8,
107 impl: []const u8,
108 args_hash: ArgsPositionMap,
109
110 fn init(self: *Pattern, allocator: mem.Allocator, template: [2][]const u8) Error!void {
111 const source = template[0];
112 const impl = template[1];
113
114 var tok_list = std.ArrayList(CToken).init(allocator);
115 defer tok_list.deinit();
116 try tokenizeMacro(source, &tok_list);
117 const tokens = try allocator.dupe(CToken, tok_list.items);
118
119 self.* = .{
120 .tokens = tokens,
121 .source = source,
122 .impl = impl,
123 .args_hash = .{},
124 };
125 const ms = MacroSlicer{ .source = source, .tokens = tokens };
126 buildArgsHash(allocator, ms, &self.args_hash) catch |err| switch (err) {
127 error.UnexpectedMacroToken => unreachable,
128 else => |e| return e,
129 };
130 }
131
132 fn deinit(self: *Pattern, allocator: mem.Allocator) void {
133 self.args_hash.deinit(allocator);
134 allocator.free(self.tokens);
135 }
136
137 /// This function assumes that `ms` has already been validated to contain a function-like
138 /// macro, and that the parsed template macro in `self` also contains a function-like
139 /// macro. Please review this logic carefully if changing that assumption. Two
140 /// function-like macros are considered equivalent if and only if they contain the same
141 /// list of tokens, modulo parameter names.
142 pub fn isEquivalent(self: Pattern, ms: MacroSlicer, args_hash: ArgsPositionMap) bool {
143 if (self.tokens.len != ms.tokens.len) return false;
144 if (args_hash.count() != self.args_hash.count()) return false;
145
146 var i: usize = 2;
147 while (self.tokens[i].id != .r_paren) : (i += 1) {}
148
149 const pattern_slicer = MacroSlicer{ .source = self.source, .tokens = self.tokens };
150 while (i < self.tokens.len) : (i += 1) {
151 const pattern_token = self.tokens[i];
152 const macro_token = ms.tokens[i];
153 if (pattern_token.id != macro_token.id) return false;
154
155 const pattern_bytes = pattern_slicer.slice(pattern_token);
156 const macro_bytes = ms.slice(macro_token);
157 switch (pattern_token.id) {
158 .identifier, .extended_identifier => {
159 const pattern_arg_index = self.args_hash.get(pattern_bytes);
160 const macro_arg_index = args_hash.get(macro_bytes);
161
162 if (pattern_arg_index == null and macro_arg_index == null) {
163 if (!mem.eql(u8, pattern_bytes, macro_bytes)) return false;
164 } else if (pattern_arg_index != null and macro_arg_index != null) {
165 if (pattern_arg_index.? != macro_arg_index.?) return false;
166 } else {
167 return false;
168 }
169 },
170 .string_literal, .char_literal, .pp_num => {
171 if (!mem.eql(u8, pattern_bytes, macro_bytes)) return false;
172 },
173 else => {
174 // other tags correspond to keywords and operators that do not contain a "payload"
175 // that can vary
176 },
177 }
178 }
179 return true;
180 }
181 };
182
183 pub fn init(allocator: mem.Allocator) Error!PatternList {
184 const patterns = try allocator.alloc(Pattern, templates.len);
185 for (templates, 0..) |template, i| {
186 try patterns[i].init(allocator, template);
187 }
188 return PatternList{ .patterns = patterns };
189 }
190
191 pub fn deinit(self: *PatternList, allocator: mem.Allocator) void {
192 for (self.patterns) |*pattern| pattern.deinit(allocator);
193 allocator.free(self.patterns);
194 }
195
196 pub fn match(self: PatternList, allocator: mem.Allocator, ms: MacroSlicer) Error!?Pattern {
197 var args_hash: ArgsPositionMap = .{};
198 defer args_hash.deinit(allocator);
199
200 buildArgsHash(allocator, ms, &args_hash) catch |err| switch (err) {
201 error.UnexpectedMacroToken => return null,
202 else => |e| return e,
203 };
204
205 for (self.patterns) |pattern| if (pattern.isEquivalent(ms, args_hash)) return pattern;
206 return null;
207 }
208};
209
210pub const MacroSlicer = struct {
211 source: []const u8,
212 tokens: []const CToken,
213
214 pub fn slice(self: MacroSlicer, token: CToken) []const u8 {
215 return self.source[token.start..token.end];
216 }
217};
218
219// Maps macro parameter names to token position, for determining if different
220// identifiers refer to the same positional argument in different macros.
221pub const ArgsPositionMap = std.StringArrayHashMapUnmanaged(usize);
222
223pub const Error = std.mem.Allocator.Error;
224pub const MacroProcessingError = Error || error{UnexpectedMacroToken};
225pub const TypeError = Error || error{UnsupportedType};
226pub const TransError = TypeError || error{UnsupportedTranslation};
227
228pub const SymbolTable = std.StringArrayHashMap(ast.Node);
229pub const AliasList = std.ArrayList(struct {
230 alias: []const u8,
231 name: []const u8,
232});
233
234pub const ResultUsed = enum {
235 used,
236 unused,
237};
238
239pub fn ScopeExtra(comptime ScopeExtraContext: type, comptime ScopeExtraType: type) type {
240 return struct {
241 id: Id,
242 parent: ?*ScopeExtraScope,
243
244 const ScopeExtraScope = @This();
245
246 pub const Id = enum {
247 block,
248 root,
249 condition,
250 loop,
251 do_loop,
252 };
253
254 /// Used for the scope of condition expressions, for example `if (cond)`.
255 /// The block is lazily initialised because it is only needed for rare
256 /// cases of comma operators being used.
257 pub const Condition = struct {
258 base: ScopeExtraScope,
259 block: ?Block = null,
260
261 pub fn getBlockScope(self: *Condition, c: *ScopeExtraContext) !*Block {
262 if (self.block) |*b| return b;
263 self.block = try Block.init(c, &self.base, true);
264 return &self.block.?;
265 }
266
267 pub fn deinit(self: *Condition) void {
268 if (self.block) |*b| b.deinit();
269 }
270 };
271
272 /// Represents an in-progress Node.Block. This struct is stack-allocated.
273 /// When it is deinitialized, it produces an Node.Block which is allocated
274 /// into the main arena.
275 pub const Block = struct {
276 base: ScopeExtraScope,
277 statements: std.ArrayList(ast.Node),
278 variables: AliasList,
279 mangle_count: u32 = 0,
280 label: ?[]const u8 = null,
281
282 /// By default all variables are discarded, since we do not know in advance if they
283 /// will be used. This maps the variable's name to the Discard payload, so that if
284 /// the variable is subsequently referenced we can indicate that the discard should
285 /// be skipped during the intermediate AST -> Zig AST render step.
286 variable_discards: std.StringArrayHashMap(*ast.Payload.Discard),
287
288 /// When the block corresponds to a function, keep track of the return type
289 /// so that the return expression can be cast, if necessary
290 return_type: ?ScopeExtraType = null,
291
292 /// C static local variables are wrapped in a block-local struct. The struct
293 /// is named after the (mangled) variable name, the Zig variable within the
294 /// struct itself is given this name.
295 pub const static_inner_name = "static";
296
297 /// C extern variables declared within a block are wrapped in a block-local
298 /// struct. The struct is named ExternLocal_[variable_name], the Zig variable
299 /// within the struct itself is [variable_name] by neccessity since it's an
300 /// extern reference to an existing symbol.
301 pub const extern_inner_prepend = "ExternLocal";
302
303 pub fn init(c: *ScopeExtraContext, parent: *ScopeExtraScope, labeled: bool) !Block {
304 var blk = Block{
305 .base = .{
306 .id = .block,
307 .parent = parent,
308 },
309 .statements = std.ArrayList(ast.Node).init(c.gpa),
310 .variables = AliasList.init(c.gpa),
311 .variable_discards = std.StringArrayHashMap(*ast.Payload.Discard).init(c.gpa),
312 };
313 if (labeled) {
314 blk.label = try blk.makeMangledName(c, "blk");
315 }
316 return blk;
317 }
318
319 pub fn deinit(self: *Block) void {
320 self.statements.deinit();
321 self.variables.deinit();
322 self.variable_discards.deinit();
323 self.* = undefined;
324 }
325
326 pub fn complete(self: *Block, c: *ScopeExtraContext) !ast.Node {
327 if (self.base.parent.?.id == .do_loop) {
328 // We reserve 1 extra statement if the parent is a do_loop. This is in case of
329 // do while, we want to put `if (cond) break;` at the end.
330 const alloc_len = self.statements.items.len + @intFromBool(self.base.parent.?.id == .do_loop);
331 var stmts = try c.arena.alloc(ast.Node, alloc_len);
332 stmts.len = self.statements.items.len;
333 @memcpy(stmts[0..self.statements.items.len], self.statements.items);
334 return ast.Node.Tag.block.create(c.arena, .{
335 .label = self.label,
336 .stmts = stmts,
337 });
338 }
339 if (self.statements.items.len == 0) return ast.Node.Tag.empty_block.init();
340 return ast.Node.Tag.block.create(c.arena, .{
341 .label = self.label,
342 .stmts = try c.arena.dupe(ast.Node, self.statements.items),
343 });
344 }
345
346 /// Given the desired name, return a name that does not shadow anything from outer scopes.
347 /// Inserts the returned name into the scope.
348 /// The name will not be visible to callers of getAlias.
349 pub fn reserveMangledName(scope: *Block, c: *ScopeExtraContext, name: []const u8) ![]const u8 {
350 return scope.createMangledName(c, name, true);
351 }
352
353 /// Same as reserveMangledName, but enables the alias immediately.
354 pub fn makeMangledName(scope: *Block, c: *ScopeExtraContext, name: []const u8) ![]const u8 {
355 return scope.createMangledName(c, name, false);
356 }
357
358 pub fn createMangledName(scope: *Block, c: *ScopeExtraContext, name: []const u8, reservation: bool) ![]const u8 {
359 const name_copy = try c.arena.dupe(u8, name);
360 var proposed_name = name_copy;
361 while (scope.contains(proposed_name)) {
362 scope.mangle_count += 1;
363 proposed_name = try std.fmt.allocPrint(c.arena, "{s}_{d}", .{ name, scope.mangle_count });
364 }
365 const new_mangle = try scope.variables.addOne();
366 if (reservation) {
367 new_mangle.* = .{ .name = name_copy, .alias = name_copy };
368 } else {
369 new_mangle.* = .{ .name = name_copy, .alias = proposed_name };
370 }
371 return proposed_name;
372 }
373
374 pub fn getAlias(scope: *Block, name: []const u8) []const u8 {
375 for (scope.variables.items) |p| {
376 if (std.mem.eql(u8, p.name, name))
377 return p.alias;
378 }
379 return scope.base.parent.?.getAlias(name);
380 }
381
382 /// Finds the (potentially) mangled struct name for a locally scoped extern variable given the original declaration name.
383 ///
384 /// Block scoped extern declarations translate to:
385 /// const MangledStructName = struct {extern [qualifiers] original_extern_variable_name: [type]};
386 /// This finds MangledStructName given original_extern_variable_name for referencing correctly in transDeclRefExpr()
387 pub fn getLocalExternAlias(scope: *Block, name: []const u8) ?[]const u8 {
388 for (scope.statements.items) |node| {
389 if (node.tag() == .extern_local_var) {
390 const parent_node = node.castTag(.extern_local_var).?;
391 const init_node = parent_node.data.init.castTag(.var_decl).?;
392 if (std.mem.eql(u8, init_node.data.name, name)) {
393 return parent_node.data.name;
394 }
395 }
396 }
397 return null;
398 }
399
400 pub fn localContains(scope: *Block, name: []const u8) bool {
401 for (scope.variables.items) |p| {
402 if (std.mem.eql(u8, p.alias, name))
403 return true;
404 }
405 return false;
406 }
407
408 pub fn contains(scope: *Block, name: []const u8) bool {
409 if (scope.localContains(name))
410 return true;
411 return scope.base.parent.?.contains(name);
412 }
413
414 pub fn discardVariable(scope: *Block, c: *ScopeExtraContext, name: []const u8) Error!void {
415 const name_node = try ast.Node.Tag.identifier.create(c.arena, name);
416 const discard = try ast.Node.Tag.discard.create(c.arena, .{ .should_skip = false, .value = name_node });
417 try scope.statements.append(discard);
418 try scope.variable_discards.putNoClobber(name, discard.castTag(.discard).?);
419 }
420 };
421
422 pub const Root = struct {
423 base: ScopeExtraScope,
424 sym_table: SymbolTable,
425 blank_macros: std.StringArrayHashMap(void),
426 context: *ScopeExtraContext,
427 nodes: std.ArrayList(ast.Node),
428
429 pub fn init(c: *ScopeExtraContext) Root {
430 return .{
431 .base = .{
432 .id = .root,
433 .parent = null,
434 },
435 .sym_table = SymbolTable.init(c.gpa),
436 .blank_macros = std.StringArrayHashMap(void).init(c.gpa),
437 .context = c,
438 .nodes = std.ArrayList(ast.Node).init(c.gpa),
439 };
440 }
441
442 pub fn deinit(scope: *Root) void {
443 scope.sym_table.deinit();
444 scope.blank_macros.deinit();
445 scope.nodes.deinit();
446 }
447
448 /// Check if the global scope contains this name, without looking into the "future", e.g.
449 /// ignore the preprocessed decl and macro names.
450 pub fn containsNow(scope: *Root, name: []const u8) bool {
451 return scope.sym_table.contains(name);
452 }
453
454 /// Check if the global scope contains the name, includes all decls that haven't been translated yet.
455 pub fn contains(scope: *Root, name: []const u8) bool {
456 return scope.containsNow(name) or scope.context.global_names.contains(name) or scope.context.weak_global_names.contains(name);
457 }
458 };
459
460 pub fn findBlockScope(inner: *ScopeExtraScope, c: *ScopeExtraContext) !*Block {
461 var scope = inner;
462 while (true) {
463 switch (scope.id) {
464 .root => unreachable,
465 .block => return @fieldParentPtr("base", scope),
466 .condition => return @as(*Condition, @fieldParentPtr("base", scope)).getBlockScope(c),
467 else => scope = scope.parent.?,
468 }
469 }
470 }
471
472 pub fn findBlockReturnType(inner: *ScopeExtraScope) ScopeExtraType {
473 var scope = inner;
474 while (true) {
475 switch (scope.id) {
476 .root => unreachable,
477 .block => {
478 const block: *Block = @fieldParentPtr("base", scope);
479 if (block.return_type) |ty| return ty;
480 scope = scope.parent.?;
481 },
482 else => scope = scope.parent.?,
483 }
484 }
485 }
486
487 pub fn getAlias(scope: *ScopeExtraScope, name: []const u8) []const u8 {
488 return switch (scope.id) {
489 .root => name,
490 .block => @as(*Block, @fieldParentPtr("base", scope)).getAlias(name),
491 .loop, .do_loop, .condition => scope.parent.?.getAlias(name),
492 };
493 }
494
495 pub fn getLocalExternAlias(scope: *ScopeExtraScope, name: []const u8) ?[]const u8 {
496 return switch (scope.id) {
497 .root => null,
498 .block => ret: {
499 const block = @as(*Block, @fieldParentPtr("base", scope));
500 break :ret block.getLocalExternAlias(name);
501 },
502 .loop, .do_loop, .condition => scope.parent.?.getLocalExternAlias(name),
503 };
504 }
505
506 pub fn contains(scope: *ScopeExtraScope, name: []const u8) bool {
507 return switch (scope.id) {
508 .root => @as(*Root, @fieldParentPtr("base", scope)).contains(name),
509 .block => @as(*Block, @fieldParentPtr("base", scope)).contains(name),
510 .loop, .do_loop, .condition => scope.parent.?.contains(name),
511 };
512 }
513
514 pub fn getBreakableScope(inner: *ScopeExtraScope) *ScopeExtraScope {
515 var scope = inner;
516 while (true) {
517 switch (scope.id) {
518 .root => unreachable,
519 .loop, .do_loop => return scope,
520 else => scope = scope.parent.?,
521 }
522 }
523 }
524
525 /// Appends a node to the first block scope if inside a function, or to the root tree if not.
526 pub fn appendNode(inner: *ScopeExtraScope, node: ast.Node) !void {
527 var scope = inner;
528 while (true) {
529 switch (scope.id) {
530 .root => {
531 const root: *Root = @fieldParentPtr("base", scope);
532 return root.nodes.append(node);
533 },
534 .block => {
535 const block: *Block = @fieldParentPtr("base", scope);
536 return block.statements.append(node);
537 },
538 else => scope = scope.parent.?,
539 }
540 }
541 }
542
543 pub fn skipVariableDiscard(inner: *ScopeExtraScope, name: []const u8) void {
544 if (true) {
545 // TODO: due to 'local variable is never mutated' errors, we can
546 // only skip discards if a variable is used as an lvalue, which
547 // we don't currently have detection for in translate-c.
548 // Once #17584 is completed, perhaps we can do away with this
549 // logic entirely, and instead rely on render to fixup code.
550 return;
551 }
552 var scope = inner;
553 while (true) {
554 switch (scope.id) {
555 .root => return,
556 .block => {
557 const block: *Block = @fieldParentPtr("base", scope);
558 if (block.variable_discards.get(name)) |discard| {
559 discard.data.should_skip = true;
560 return;
561 }
562 },
563 else => {},
564 }
565 scope = scope.parent.?;
566 }
567 }
568 };
569}
570
571pub fn tokenizeMacro(source: []const u8, tok_list: *std.ArrayList(CToken)) Error!void {
572 var tokenizer: Tokenizer = .{
573 .buf = source,
574 .source = .unused,
575 .langopts = .{},
576 };
577 while (true) {
578 const tok = tokenizer.next();
579 switch (tok.id) {
580 .whitespace => continue,
581 .nl, .eof => {
582 try tok_list.append(tok);
583 break;
584 },
585 else => {},
586 }
587 try tok_list.append(tok);
588 }
589}
src/translate_c/ast.zig created+3027
...@@ -0,0 +1,3027 @@
1const std = @import("std");
2const Allocator = std.mem.Allocator;
3
4pub const Node = extern union {
5 /// If the tag value is less than Tag.no_payload_count, then no pointer
6 /// dereference is needed.
7 tag_if_small_enough: usize,
8 ptr_otherwise: *Payload,
9
10 pub const Tag = enum {
11 /// Declarations add themselves to the correct scopes and should not be emitted as this tag.
12 declaration,
13 null_literal,
14 undefined_literal,
15 /// opaque {}
16 opaque_literal,
17 true_literal,
18 false_literal,
19 empty_block,
20 return_void,
21 zero_literal,
22 one_literal,
23 void_type,
24 noreturn_type,
25 @"anytype",
26 @"continue",
27 @"break",
28 // After this, the tag requires a payload.
29
30 integer_literal,
31 float_literal,
32 string_literal,
33 char_literal,
34 enum_literal,
35 /// "string"[0..end]
36 string_slice,
37 identifier,
38 fn_identifier,
39 @"if",
40 /// if (!operand) break;
41 if_not_break,
42 @"while",
43 /// while (true) operand
44 while_true,
45 @"switch",
46 /// else => operand,
47 switch_else,
48 /// items => body,
49 switch_prong,
50 break_val,
51 @"return",
52 field_access,
53 array_access,
54 call,
55 var_decl,
56 /// const name = struct { init }
57 static_local_var,
58 /// const ExternLocal_name = struct { init }
59 extern_local_var,
60 /// var name = init.*
61 mut_str,
62 func,
63 warning,
64 @"struct",
65 @"union",
66 @"comptime",
67 @"defer",
68 array_init,
69 tuple,
70 container_init,
71 container_init_dot,
72 helpers_cast,
73 /// _ = operand;
74 discard,
75
76 // a + b
77 add,
78 // a = b
79 add_assign,
80 // c = (a = b)
81 add_wrap,
82 add_wrap_assign,
83 sub,
84 sub_assign,
85 sub_wrap,
86 sub_wrap_assign,
87 mul,
88 mul_assign,
89 mul_wrap,
90 mul_wrap_assign,
91 div,
92 div_assign,
93 shl,
94 shl_assign,
95 shr,
96 shr_assign,
97 mod,
98 mod_assign,
99 @"and",
100 @"or",
101 less_than,
102 less_than_equal,
103 greater_than,
104 greater_than_equal,
105 equal,
106 not_equal,
107 bit_and,
108 bit_and_assign,
109 bit_or,
110 bit_or_assign,
111 bit_xor,
112 bit_xor_assign,
113 array_cat,
114 ellipsis3,
115 assign,
116
117 /// @import("std").zig.c_builtins.<name>
118 import_c_builtin,
119 /// @intCast(operand)
120 int_cast,
121 /// @constCast(operand)
122 const_cast,
123 /// @volatileCast(operand)
124 volatile_cast,
125 /// @import("std").zig.c_translation.promoteIntLiteral(value, type, base)
126 helpers_promoteIntLiteral,
127 /// @import("std").zig.c_translation.signedRemainder(lhs, rhs)
128 signed_remainder,
129 /// @divTrunc(lhs, rhs)
130 div_trunc,
131 /// @intFromBool(operand)
132 int_from_bool,
133 /// @as(lhs, rhs)
134 as,
135 /// @truncate(operand)
136 truncate,
137 /// @bitCast(operand)
138 bit_cast,
139 /// @floatCast(operand)
140 float_cast,
141 /// @intFromFloat(operand)
142 int_from_float,
143 /// @floatFromInt(operand)
144 float_from_int,
145 /// @ptrFromInt(operand)
146 ptr_from_int,
147 /// @intFromPtr(operand)
148 int_from_ptr,
149 /// @alignCast(operand)
150 align_cast,
151 /// @ptrCast(operand)
152 ptr_cast,
153 /// @divExact(lhs, rhs)
154 div_exact,
155 /// @offsetOf(lhs, rhs)
156 offset_of,
157 /// @splat(operand)
158 vector_zero_init,
159 /// @shuffle(type, a, b, mask)
160 shuffle,
161 /// @extern(ty, .{ .name = n })
162 builtin_extern,
163
164 /// @import("std").zig.c_translation.MacroArithmetic.<op>(lhs, rhs)
165 macro_arithmetic,
166
167 asm_simple,
168
169 negate,
170 negate_wrap,
171 bit_not,
172 not,
173 address_of,
174 /// .?
175 unwrap,
176 /// .*
177 deref,
178
179 block,
180 /// { operand }
181 block_single,
182
183 sizeof,
184 alignof,
185 typeof,
186 typeinfo,
187 type,
188
189 optional_type,
190 c_pointer,
191 single_pointer,
192 array_type,
193 null_sentinel_array_type,
194
195 /// @import("std").zig.c_translation.sizeof(operand)
196 helpers_sizeof,
197 /// @import("std").zig.c_translation.FlexibleArrayType(lhs, rhs)
198 helpers_flexible_array_type,
199 /// @import("std").zig.c_translation.shuffleVectorIndex(lhs, rhs)
200 helpers_shuffle_vector_index,
201 /// @import("std").zig.c_translation.Macro.<operand>
202 helpers_macro,
203 /// @Vector(lhs, rhs)
204 vector,
205 /// @import("std").mem.zeroes(operand)
206 std_mem_zeroes,
207 /// @import("std").mem.zeroInit(lhs, rhs)
208 std_mem_zeroinit,
209 // pub const name = @compileError(msg);
210 fail_decl,
211 // var actual = mangled;
212 arg_redecl,
213 /// pub const alias = actual;
214 alias,
215 /// const name = init;
216 var_simple,
217 /// pub const name = init;
218 pub_var_simple,
219 /// pub? const name (: type)? = value
220 enum_constant,
221
222 /// pub inline fn name(params) return_type body
223 pub_inline_fn,
224
225 /// [0]type{}
226 empty_array,
227 /// [1]type{val} ** count
228 array_filler,
229
230 pub const last_no_payload_tag = Tag.@"break";
231 pub const no_payload_count = @intFromEnum(last_no_payload_tag) + 1;
232
233 pub fn Type(comptime t: Tag) type {
234 return switch (t) {
235 .declaration,
236 .null_literal,
237 .undefined_literal,
238 .opaque_literal,
239 .true_literal,
240 .false_literal,
241 .empty_block,
242 .return_void,
243 .zero_literal,
244 .one_literal,
245 .void_type,
246 .noreturn_type,
247 .@"anytype",
248 .@"continue",
249 .@"break",
250 => @compileError("Type Tag " ++ @tagName(t) ++ " has no payload"),
251
252 .std_mem_zeroes,
253 .@"return",
254 .@"comptime",
255 .@"defer",
256 .asm_simple,
257 .negate,
258 .negate_wrap,
259 .bit_not,
260 .not,
261 .optional_type,
262 .address_of,
263 .unwrap,
264 .deref,
265 .int_from_ptr,
266 .empty_array,
267 .while_true,
268 .if_not_break,
269 .switch_else,
270 .block_single,
271 .helpers_sizeof,
272 .int_from_bool,
273 .sizeof,
274 .alignof,
275 .typeof,
276 .typeinfo,
277 .align_cast,
278 .truncate,
279 .bit_cast,
280 .float_cast,
281 .int_from_float,
282 .float_from_int,
283 .ptr_from_int,
284 .ptr_cast,
285 .int_cast,
286 .const_cast,
287 .volatile_cast,
288 .vector_zero_init,
289 => Payload.UnOp,
290
291 .add,
292 .add_assign,
293 .add_wrap,
294 .add_wrap_assign,
295 .sub,
296 .sub_assign,
297 .sub_wrap,
298 .sub_wrap_assign,
299 .mul,
300 .mul_assign,
301 .mul_wrap,
302 .mul_wrap_assign,
303 .div,
304 .div_assign,
305 .shl,
306 .shl_assign,
307 .shr,
308 .shr_assign,
309 .mod,
310 .mod_assign,
311 .@"and",
312 .@"or",
313 .less_than,
314 .less_than_equal,
315 .greater_than,
316 .greater_than_equal,
317 .equal,
318 .not_equal,
319 .bit_and,
320 .bit_and_assign,
321 .bit_or,
322 .bit_or_assign,
323 .bit_xor,
324 .bit_xor_assign,
325 .div_trunc,
326 .signed_remainder,
327 .as,
328 .array_cat,
329 .ellipsis3,
330 .assign,
331 .array_access,
332 .std_mem_zeroinit,
333 .helpers_flexible_array_type,
334 .helpers_shuffle_vector_index,
335 .vector,
336 .div_exact,
337 .offset_of,
338 .helpers_cast,
339 => Payload.BinOp,
340
341 .integer_literal,
342 .float_literal,
343 .string_literal,
344 .char_literal,
345 .enum_literal,
346 .identifier,
347 .fn_identifier,
348 .warning,
349 .type,
350 .helpers_macro,
351 .import_c_builtin,
352 => Payload.Value,
353 .discard => Payload.Discard,
354 .@"if" => Payload.If,
355 .@"while" => Payload.While,
356 .@"switch", .array_init, .switch_prong => Payload.Switch,
357 .break_val => Payload.BreakVal,
358 .call => Payload.Call,
359 .var_decl => Payload.VarDecl,
360 .func => Payload.Func,
361 .@"struct", .@"union" => Payload.Record,
362 .tuple => Payload.TupleInit,
363 .container_init => Payload.ContainerInit,
364 .container_init_dot => Payload.ContainerInitDot,
365 .helpers_promoteIntLiteral => Payload.PromoteIntLiteral,
366 .block => Payload.Block,
367 .c_pointer, .single_pointer => Payload.Pointer,
368 .array_type, .null_sentinel_array_type => Payload.Array,
369 .arg_redecl, .alias, .fail_decl => Payload.ArgRedecl,
370 .var_simple, .pub_var_simple, .static_local_var, .extern_local_var, .mut_str => Payload.SimpleVarDecl,
371 .enum_constant => Payload.EnumConstant,
372 .array_filler => Payload.ArrayFiller,
373 .pub_inline_fn => Payload.PubInlineFn,
374 .field_access => Payload.FieldAccess,
375 .string_slice => Payload.StringSlice,
376 .shuffle => Payload.Shuffle,
377 .builtin_extern => Payload.Extern,
378 .macro_arithmetic => Payload.MacroArithmetic,
379 };
380 }
381
382 pub fn init(comptime t: Tag) Node {
383 comptime std.debug.assert(@intFromEnum(t) < Tag.no_payload_count);
384 return .{ .tag_if_small_enough = @intFromEnum(t) };
385 }
386
387 pub fn create(comptime t: Tag, ally: Allocator, data: Data(t)) error{OutOfMemory}!Node {
388 const ptr = try ally.create(t.Type());
389 ptr.* = .{
390 .base = .{ .tag = t },
391 .data = data,
392 };
393 return Node{ .ptr_otherwise = &ptr.base };
394 }
395
396 pub fn Data(comptime t: Tag) type {
397 return std.meta.fieldInfo(t.Type(), .data).type;
398 }
399 };
400
401 pub fn tag(self: Node) Tag {
402 if (self.tag_if_small_enough < Tag.no_payload_count) {
403 return @as(Tag, @enumFromInt(@as(std.meta.Tag(Tag), @intCast(self.tag_if_small_enough))));
404 } else {
405 return self.ptr_otherwise.tag;
406 }
407 }
408
409 pub fn castTag(self: Node, comptime t: Tag) ?*t.Type() {
410 if (self.tag_if_small_enough < Tag.no_payload_count)
411 return null;
412
413 if (self.ptr_otherwise.tag == t)
414 return @alignCast(@fieldParentPtr("base", self.ptr_otherwise));
415
416 return null;
417 }
418
419 pub fn initPayload(payload: *Payload) Node {
420 std.debug.assert(@intFromEnum(payload.tag) >= Tag.no_payload_count);
421 return .{ .ptr_otherwise = payload };
422 }
423
424 pub fn isNoreturn(node: Node, break_counts: bool) bool {
425 switch (node.tag()) {
426 .block => {
427 const block_node = node.castTag(.block).?;
428 if (block_node.data.stmts.len == 0) return false;
429
430 const last = block_node.data.stmts[block_node.data.stmts.len - 1];
431 return last.isNoreturn(break_counts);
432 },
433 .@"switch" => {
434 const switch_node = node.castTag(.@"switch").?;
435
436 for (switch_node.data.cases) |case| {
437 const body = if (case.castTag(.switch_else)) |some|
438 some.data
439 else if (case.castTag(.switch_prong)) |some|
440 some.data.cond
441 else
442 unreachable;
443
444 if (!body.isNoreturn(break_counts)) return false;
445 }
446 return true;
447 },
448 .@"return", .return_void => return true,
449 .@"break" => if (break_counts) return true,
450 else => {},
451 }
452 return false;
453 }
454};
455
456pub const Payload = struct {
457 tag: Node.Tag,
458
459 pub const Value = struct {
460 base: Payload,
461 data: []const u8,
462 };
463
464 pub const UnOp = struct {
465 base: Payload,
466 data: Node,
467 };
468
469 pub const BinOp = struct {
470 base: Payload,
471 data: struct {
472 lhs: Node,
473 rhs: Node,
474 },
475 };
476
477 pub const Discard = struct {
478 base: Payload,
479 data: struct {
480 should_skip: bool,
481 value: Node,
482 },
483 };
484
485 pub const If = struct {
486 base: Payload,
487 data: struct {
488 cond: Node,
489 then: Node,
490 @"else": ?Node,
491 },
492 };
493
494 pub const While = struct {
495 base: Payload,
496 data: struct {
497 cond: Node,
498 body: Node,
499 cont_expr: ?Node,
500 },
501 };
502
503 pub const Switch = struct {
504 base: Payload,
505 data: struct {
506 cond: Node,
507 cases: []Node,
508 },
509 };
510
511 pub const BreakVal = struct {
512 base: Payload,
513 data: struct {
514 label: ?[]const u8,
515 val: Node,
516 },
517 };
518
519 pub const Call = struct {
520 base: Payload,
521 data: struct {
522 lhs: Node,
523 args: []Node,
524 },
525 };
526
527 pub const VarDecl = struct {
528 base: Payload,
529 data: struct {
530 is_pub: bool,
531 is_const: bool,
532 is_extern: bool,
533 is_export: bool,
534 is_threadlocal: bool,
535 alignment: ?c_uint,
536 linksection_string: ?[]const u8,
537 name: []const u8,
538 type: Node,
539 init: ?Node,
540 },
541 };
542
543 pub const Func = struct {
544 base: Payload,
545 data: struct {
546 is_pub: bool,
547 is_extern: bool,
548 is_export: bool,
549 is_inline: bool,
550 is_var_args: bool,
551 name: ?[]const u8,
552 linksection_string: ?[]const u8,
553 explicit_callconv: ?CallingConvention,
554 params: []Param,
555 return_type: Node,
556 body: ?Node,
557 alignment: ?c_uint,
558 },
559
560 pub const CallingConvention = enum {
561 c,
562 x86_64_sysv,
563 x86_64_win,
564 x86_stdcall,
565 x86_fastcall,
566 x86_thiscall,
567 x86_vectorcall,
568 aarch64_vfabi,
569 arm_aapcs,
570 arm_aapcs_vfp,
571 m68k_rtd,
572 };
573 };
574
575 pub const Param = struct {
576 is_noalias: bool,
577 name: ?[]const u8,
578 type: Node,
579 };
580
581 pub const Record = struct {
582 base: Payload,
583 data: struct {
584 layout: enum { @"packed", @"extern", none },
585 fields: []Field,
586 functions: []Node,
587 variables: []Node,
588 },
589
590 pub const Field = struct {
591 name: []const u8,
592 type: Node,
593 alignment: ?c_uint,
594 default_value: ?Node,
595 };
596 };
597
598 pub const TupleInit = struct {
599 base: Payload,
600 data: []Node,
601 };
602
603 pub const ContainerInit = struct {
604 base: Payload,
605 data: struct {
606 lhs: Node,
607 inits: []Initializer,
608 },
609
610 pub const Initializer = struct {
611 name: []const u8,
612 value: Node,
613 };
614 };
615
616 pub const ContainerInitDot = struct {
617 base: Payload,
618 data: []Initializer,
619
620 pub const Initializer = struct {
621 name: []const u8,
622 value: Node,
623 };
624 };
625
626 pub const Block = struct {
627 base: Payload,
628 data: struct {
629 label: ?[]const u8,
630 stmts: []Node,
631 },
632 };
633
634 pub const Array = struct {
635 base: Payload,
636 data: ArrayTypeInfo,
637
638 pub const ArrayTypeInfo = struct {
639 elem_type: Node,
640 len: usize,
641 };
642 };
643
644 pub const Pointer = struct {
645 base: Payload,
646 data: struct {
647 elem_type: Node,
648 is_const: bool,
649 is_volatile: bool,
650 },
651 };
652
653 pub const ArgRedecl = struct {
654 base: Payload,
655 data: struct {
656 actual: []const u8,
657 mangled: []const u8,
658 },
659 };
660
661 pub const SimpleVarDecl = struct {
662 base: Payload,
663 data: struct {
664 name: []const u8,
665 init: Node,
666 },
667 };
668
669 pub const EnumConstant = struct {
670 base: Payload,
671 data: struct {
672 name: []const u8,
673 is_public: bool,
674 type: ?Node,
675 value: Node,
676 },
677 };
678
679 pub const ArrayFiller = struct {
680 base: Payload,
681 data: struct {
682 type: Node,
683 filler: Node,
684 count: usize,
685 },
686 };
687
688 pub const PubInlineFn = struct {
689 base: Payload,
690 data: struct {
691 name: []const u8,
692 params: []Param,
693 return_type: Node,
694 body: Node,
695 },
696 };
697
698 pub const FieldAccess = struct {
699 base: Payload,
700 data: struct {
701 lhs: Node,
702 field_name: []const u8,
703 },
704 };
705
706 pub const PromoteIntLiteral = struct {
707 base: Payload,
708 data: struct {
709 value: Node,
710 type: Node,
711 base: Node,
712 },
713 };
714
715 pub const StringSlice = struct {
716 base: Payload,
717 data: struct {
718 string: Node,
719 end: usize,
720 },
721 };
722
723 pub const Shuffle = struct {
724 base: Payload,
725 data: struct {
726 element_type: Node,
727 a: Node,
728 b: Node,
729 mask_vector: Node,
730 },
731 };
732
733 pub const Extern = struct {
734 base: Payload,
735 data: struct {
736 type: Node,
737 name: Node,
738 },
739 };
740
741 pub const MacroArithmetic = struct {
742 base: Payload,
743 data: struct {
744 op: Operator,
745 lhs: Node,
746 rhs: Node,
747 },
748
749 pub const Operator = enum { div, rem };
750 };
751};
752
753/// Converts the nodes into a Zig Ast.
754/// Caller must free the source slice.
755pub fn render(gpa: Allocator, nodes: []const Node) !std.zig.Ast {
756 var ctx = Context{
757 .gpa = gpa,
758 .buf = std.ArrayList(u8).init(gpa),
759 };
760 defer ctx.buf.deinit();
761 defer ctx.nodes.deinit(gpa);
762 defer ctx.extra_data.deinit(gpa);
763 defer ctx.tokens.deinit(gpa);
764
765 // Estimate that each top level node has 10 child nodes.
766 const estimated_node_count = nodes.len * 10;
767 try ctx.nodes.ensureTotalCapacity(gpa, estimated_node_count);
768 // Estimate that each each node has 2 tokens.
769 const estimated_tokens_count = estimated_node_count * 2;
770 try ctx.tokens.ensureTotalCapacity(gpa, estimated_tokens_count);
771 // Estimate that each each token is 3 bytes long.
772 const estimated_buf_len = estimated_tokens_count * 3;
773 try ctx.buf.ensureTotalCapacity(estimated_buf_len);
774
775 ctx.nodes.appendAssumeCapacity(.{
776 .tag = .root,
777 .main_token = 0,
778 .data = .{
779 .lhs = undefined,
780 .rhs = undefined,
781 },
782 });
783
784 const root_members = blk: {
785 var result = std.ArrayList(NodeIndex).init(gpa);
786 defer result.deinit();
787
788 for (nodes) |node| {
789 const res = try renderNode(&ctx, node);
790 if (node.tag() == .warning) continue;
791 try result.append(res);
792 }
793 break :blk try ctx.listToSpan(result.items);
794 };
795
796 ctx.nodes.items(.data)[0] = .{
797 .lhs = root_members.start,
798 .rhs = root_members.end,
799 };
800
801 try ctx.tokens.append(gpa, .{
802 .tag = .eof,
803 .start = @as(u32, @intCast(ctx.buf.items.len)),
804 });
805
806 return std.zig.Ast{
807 .source = try ctx.buf.toOwnedSliceSentinel(0),
808 .tokens = ctx.tokens.toOwnedSlice(),
809 .nodes = ctx.nodes.toOwnedSlice(),
810 .extra_data = try ctx.extra_data.toOwnedSlice(gpa),
811 .errors = &.{},
812 .mode = .zig,
813 };
814}
815
816const NodeIndex = std.zig.Ast.Node.Index;
817const NodeSubRange = std.zig.Ast.Node.SubRange;
818const TokenIndex = std.zig.Ast.TokenIndex;
819const TokenTag = std.zig.Token.Tag;
820
821const Context = struct {
822 gpa: Allocator,
823 buf: std.ArrayList(u8),
824 nodes: std.zig.Ast.NodeList = .{},
825 extra_data: std.ArrayListUnmanaged(std.zig.Ast.Node.Index) = .empty,
826 tokens: std.zig.Ast.TokenList = .{},
827
828 fn addTokenFmt(c: *Context, tag: TokenTag, comptime format: []const u8, args: anytype) Allocator.Error!TokenIndex {
829 const start_index = c.buf.items.len;
830 try c.buf.writer().print(format ++ " ", args);
831
832 try c.tokens.append(c.gpa, .{
833 .tag = tag,
834 .start = @as(u32, @intCast(start_index)),
835 });
836
837 return @as(u32, @intCast(c.tokens.len - 1));
838 }
839
840 fn addToken(c: *Context, tag: TokenTag, bytes: []const u8) Allocator.Error!TokenIndex {
841 return c.addTokenFmt(tag, "{s}", .{bytes});
842 }
843
844 fn addIdentifier(c: *Context, bytes: []const u8) Allocator.Error!TokenIndex {
845 if (std.zig.primitives.isPrimitive(bytes))
846 return c.addTokenFmt(.identifier, "@\"{s}\"", .{bytes});
847 return c.addTokenFmt(.identifier, "{p}", .{std.zig.fmtId(bytes)});
848 }
849
850 fn listToSpan(c: *Context, list: []const NodeIndex) Allocator.Error!NodeSubRange {
851 try c.extra_data.appendSlice(c.gpa, list);
852 return NodeSubRange{
853 .start = @as(NodeIndex, @intCast(c.extra_data.items.len - list.len)),
854 .end = @as(NodeIndex, @intCast(c.extra_data.items.len)),
855 };
856 }
857
858 fn addNode(c: *Context, elem: std.zig.Ast.Node) Allocator.Error!NodeIndex {
859 const result = @as(NodeIndex, @intCast(c.nodes.len));
860 try c.nodes.append(c.gpa, elem);
861 return result;
862 }
863
864 fn addExtra(c: *Context, extra: anytype) Allocator.Error!NodeIndex {
865 const fields = std.meta.fields(@TypeOf(extra));
866 try c.extra_data.ensureUnusedCapacity(c.gpa, fields.len);
867 const result = @as(u32, @intCast(c.extra_data.items.len));
868 inline for (fields) |field| {
869 comptime std.debug.assert(field.type == NodeIndex);
870 c.extra_data.appendAssumeCapacity(@field(extra, field.name));
871 }
872 return result;
873 }
874};
875
876fn renderNodes(c: *Context, nodes: []const Node) Allocator.Error!NodeSubRange {
877 var result = std.ArrayList(NodeIndex).init(c.gpa);
878 defer result.deinit();
879
880 for (nodes) |node| {
881 const res = try renderNode(c, node);
882 if (node.tag() == .warning) continue;
883 try result.append(res);
884 }
885
886 return try c.listToSpan(result.items);
887}
888
889fn renderNode(c: *Context, node: Node) Allocator.Error!NodeIndex {
890 switch (node.tag()) {
891 .declaration => unreachable,
892 .warning => {
893 const payload = node.castTag(.warning).?.data;
894 try c.buf.append('\n');
895 try c.buf.appendSlice(payload);
896 try c.buf.append('\n');
897 return @as(NodeIndex, 0); // error: integer value 0 cannot be coerced to type 'std.mem.Allocator.Error!u32'
898 },
899 .helpers_cast => {
900 const payload = node.castTag(.helpers_cast).?.data;
901 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "cast" });
902 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
903 },
904 .helpers_promoteIntLiteral => {
905 const payload = node.castTag(.helpers_promoteIntLiteral).?.data;
906 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "promoteIntLiteral" });
907 return renderCall(c, import_node, &.{ payload.type, payload.value, payload.base });
908 },
909 .helpers_sizeof => {
910 const payload = node.castTag(.helpers_sizeof).?.data;
911 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "sizeof" });
912 return renderCall(c, import_node, &.{payload});
913 },
914 .std_mem_zeroes => {
915 const payload = node.castTag(.std_mem_zeroes).?.data;
916 const import_node = try renderStdImport(c, &.{ "mem", "zeroes" });
917 return renderCall(c, import_node, &.{payload});
918 },
919 .std_mem_zeroinit => {
920 const payload = node.castTag(.std_mem_zeroinit).?.data;
921 const import_node = try renderStdImport(c, &.{ "mem", "zeroInit" });
922 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
923 },
924 .helpers_flexible_array_type => {
925 const payload = node.castTag(.helpers_flexible_array_type).?.data;
926 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "FlexibleArrayType" });
927 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
928 },
929 .helpers_shuffle_vector_index => {
930 const payload = node.castTag(.helpers_shuffle_vector_index).?.data;
931 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "shuffleVectorIndex" });
932 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
933 },
934 .vector => {
935 const payload = node.castTag(.vector).?.data;
936 return renderBuiltinCall(c, "@Vector", &.{ payload.lhs, payload.rhs });
937 },
938 .call => {
939 const payload = node.castTag(.call).?.data;
940 // Cosmetic: avoids an unnecesary address_of on most function calls.
941 const lhs = if (payload.lhs.tag() == .fn_identifier)
942 try c.addNode(.{
943 .tag = .identifier,
944 .main_token = try c.addIdentifier(payload.lhs.castTag(.fn_identifier).?.data),
945 .data = undefined,
946 })
947 else
948 try renderNodeGrouped(c, payload.lhs);
949 return renderCall(c, lhs, payload.args);
950 },
951 .null_literal => return c.addNode(.{
952 .tag = .identifier,
953 .main_token = try c.addToken(.identifier, "null"),
954 .data = undefined,
955 }),
956 .undefined_literal => return c.addNode(.{
957 .tag = .identifier,
958 .main_token = try c.addToken(.identifier, "undefined"),
959 .data = undefined,
960 }),
961 .true_literal => return c.addNode(.{
962 .tag = .identifier,
963 .main_token = try c.addToken(.identifier, "true"),
964 .data = undefined,
965 }),
966 .false_literal => return c.addNode(.{
967 .tag = .identifier,
968 .main_token = try c.addToken(.identifier, "false"),
969 .data = undefined,
970 }),
971 .zero_literal => return c.addNode(.{
972 .tag = .number_literal,
973 .main_token = try c.addToken(.number_literal, "0"),
974 .data = undefined,
975 }),
976 .one_literal => return c.addNode(.{
977 .tag = .number_literal,
978 .main_token = try c.addToken(.number_literal, "1"),
979 .data = undefined,
980 }),
981 .void_type => return c.addNode(.{
982 .tag = .identifier,
983 .main_token = try c.addToken(.identifier, "void"),
984 .data = undefined,
985 }),
986 .noreturn_type => return c.addNode(.{
987 .tag = .identifier,
988 .main_token = try c.addToken(.identifier, "noreturn"),
989 .data = undefined,
990 }),
991 .@"continue" => return c.addNode(.{
992 .tag = .@"continue",
993 .main_token = try c.addToken(.keyword_continue, "continue"),
994 .data = .{
995 .lhs = 0,
996 .rhs = undefined,
997 },
998 }),
999 .return_void => return c.addNode(.{
1000 .tag = .@"return",
1001 .main_token = try c.addToken(.keyword_return, "return"),
1002 .data = .{
1003 .lhs = 0,
1004 .rhs = undefined,
1005 },
1006 }),
1007 .@"break" => return c.addNode(.{
1008 .tag = .@"break",
1009 .main_token = try c.addToken(.keyword_break, "break"),
1010 .data = .{
1011 .lhs = 0,
1012 .rhs = 0,
1013 },
1014 }),
1015 .break_val => {
1016 const payload = node.castTag(.break_val).?.data;
1017 const tok = try c.addToken(.keyword_break, "break");
1018 const break_label = if (payload.label) |some| blk: {
1019 _ = try c.addToken(.colon, ":");
1020 break :blk try c.addIdentifier(some);
1021 } else 0;
1022 return c.addNode(.{
1023 .tag = .@"break",
1024 .main_token = tok,
1025 .data = .{
1026 .lhs = break_label,
1027 .rhs = try renderNode(c, payload.val),
1028 },
1029 });
1030 },
1031 .@"return" => {
1032 const payload = node.castTag(.@"return").?.data;
1033 return c.addNode(.{
1034 .tag = .@"return",
1035 .main_token = try c.addToken(.keyword_return, "return"),
1036 .data = .{
1037 .lhs = try renderNode(c, payload),
1038 .rhs = undefined,
1039 },
1040 });
1041 },
1042 .@"comptime" => {
1043 const payload = node.castTag(.@"comptime").?.data;
1044 return c.addNode(.{
1045 .tag = .@"comptime",
1046 .main_token = try c.addToken(.keyword_comptime, "comptime"),
1047 .data = .{
1048 .lhs = try renderNode(c, payload),
1049 .rhs = undefined,
1050 },
1051 });
1052 },
1053 .@"defer" => {
1054 const payload = node.castTag(.@"defer").?.data;
1055 return c.addNode(.{
1056 .tag = .@"defer",
1057 .main_token = try c.addToken(.keyword_defer, "defer"),
1058 .data = .{
1059 .lhs = undefined,
1060 .rhs = try renderNode(c, payload),
1061 },
1062 });
1063 },
1064 .asm_simple => {
1065 const payload = node.castTag(.asm_simple).?.data;
1066 const asm_token = try c.addToken(.keyword_asm, "asm");
1067 _ = try c.addToken(.l_paren, "(");
1068 return c.addNode(.{
1069 .tag = .asm_simple,
1070 .main_token = asm_token,
1071 .data = .{
1072 .lhs = try renderNode(c, payload),
1073 .rhs = try c.addToken(.r_paren, ")"),
1074 },
1075 });
1076 },
1077 .type => {
1078 const payload = node.castTag(.type).?.data;
1079 return c.addNode(.{
1080 .tag = .identifier,
1081 .main_token = try c.addToken(.identifier, payload),
1082 .data = undefined,
1083 });
1084 },
1085 .identifier => {
1086 const payload = node.castTag(.identifier).?.data;
1087 return c.addNode(.{
1088 .tag = .identifier,
1089 .main_token = try c.addIdentifier(payload),
1090 .data = undefined,
1091 });
1092 },
1093 .fn_identifier => {
1094 // C semantics are that a function identifier has address
1095 // value (implicit in stage1, explicit in stage2), except in
1096 // the context of an address_of, which is handled there.
1097 const payload = node.castTag(.fn_identifier).?.data;
1098 const tok = try c.addToken(.ampersand, "&");
1099 const arg = try c.addNode(.{
1100 .tag = .identifier,
1101 .main_token = try c.addIdentifier(payload),
1102 .data = undefined,
1103 });
1104 return c.addNode(.{
1105 .tag = .address_of,
1106 .main_token = tok,
1107 .data = .{
1108 .lhs = arg,
1109 .rhs = undefined,
1110 },
1111 });
1112 },
1113 .float_literal => {
1114 const payload = node.castTag(.float_literal).?.data;
1115 return c.addNode(.{
1116 .tag = .number_literal,
1117 .main_token = try c.addToken(.number_literal, payload),
1118 .data = undefined,
1119 });
1120 },
1121 .integer_literal => {
1122 const payload = node.castTag(.integer_literal).?.data;
1123 return c.addNode(.{
1124 .tag = .number_literal,
1125 .main_token = try c.addToken(.number_literal, payload),
1126 .data = undefined,
1127 });
1128 },
1129 .string_literal => {
1130 const payload = node.castTag(.string_literal).?.data;
1131 return c.addNode(.{
1132 .tag = .string_literal,
1133 .main_token = try c.addToken(.string_literal, payload),
1134 .data = undefined,
1135 });
1136 },
1137 .char_literal => {
1138 const payload = node.castTag(.char_literal).?.data;
1139 return c.addNode(.{
1140 .tag = .char_literal,
1141 .main_token = try c.addToken(.char_literal, payload),
1142 .data = undefined,
1143 });
1144 },
1145 .enum_literal => {
1146 const payload = node.castTag(.enum_literal).?.data;
1147 _ = try c.addToken(.period, ".");
1148 return c.addNode(.{
1149 .tag = .enum_literal,
1150 .main_token = try c.addToken(.identifier, payload),
1151 .data = undefined,
1152 });
1153 },
1154 .helpers_macro => {
1155 const payload = node.castTag(.helpers_macro).?.data;
1156 const chain = [_][]const u8{
1157 "zig",
1158 "c_translation",
1159 "Macros",
1160 payload,
1161 };
1162 return renderStdImport(c, &chain);
1163 },
1164 .import_c_builtin => {
1165 const payload = node.castTag(.import_c_builtin).?.data;
1166 const chain = [_][]const u8{
1167 "zig",
1168 "c_builtins",
1169 payload,
1170 };
1171 return renderStdImport(c, &chain);
1172 },
1173 .string_slice => {
1174 const payload = node.castTag(.string_slice).?.data;
1175
1176 const string = try renderNode(c, payload.string);
1177 const l_bracket = try c.addToken(.l_bracket, "[");
1178 const start = try c.addNode(.{
1179 .tag = .number_literal,
1180 .main_token = try c.addToken(.number_literal, "0"),
1181 .data = undefined,
1182 });
1183 _ = try c.addToken(.ellipsis2, "..");
1184 const end = try c.addNode(.{
1185 .tag = .number_literal,
1186 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{payload.end}),
1187 .data = undefined,
1188 });
1189 _ = try c.addToken(.r_bracket, "]");
1190
1191 return c.addNode(.{
1192 .tag = .slice,
1193 .main_token = l_bracket,
1194 .data = .{
1195 .lhs = string,
1196 .rhs = try c.addExtra(std.zig.Ast.Node.Slice{
1197 .start = start,
1198 .end = end,
1199 }),
1200 },
1201 });
1202 },
1203 .fail_decl => {
1204 const payload = node.castTag(.fail_decl).?.data;
1205 // pub const name = @compileError(msg);
1206 _ = try c.addToken(.keyword_pub, "pub");
1207 const const_tok = try c.addToken(.keyword_const, "const");
1208 _ = try c.addIdentifier(payload.actual);
1209 _ = try c.addToken(.equal, "=");
1210
1211 const compile_error_tok = try c.addToken(.builtin, "@compileError");
1212 _ = try c.addToken(.l_paren, "(");
1213 const err_msg_tok = try c.addTokenFmt(.string_literal, "\"{}\"", .{std.zig.fmtEscapes(payload.mangled)});
1214 const err_msg = try c.addNode(.{
1215 .tag = .string_literal,
1216 .main_token = err_msg_tok,
1217 .data = undefined,
1218 });
1219 _ = try c.addToken(.r_paren, ")");
1220 const compile_error = try c.addNode(.{
1221 .tag = .builtin_call_two,
1222 .main_token = compile_error_tok,
1223 .data = .{
1224 .lhs = err_msg,
1225 .rhs = 0,
1226 },
1227 });
1228 _ = try c.addToken(.semicolon, ";");
1229
1230 return c.addNode(.{
1231 .tag = .simple_var_decl,
1232 .main_token = const_tok,
1233 .data = .{
1234 .lhs = 0,
1235 .rhs = compile_error,
1236 },
1237 });
1238 },
1239 .pub_var_simple, .var_simple => {
1240 const payload = @as(*Payload.SimpleVarDecl, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
1241 if (node.tag() == .pub_var_simple) _ = try c.addToken(.keyword_pub, "pub");
1242 const const_tok = try c.addToken(.keyword_const, "const");
1243 _ = try c.addIdentifier(payload.name);
1244 _ = try c.addToken(.equal, "=");
1245
1246 const init = try renderNode(c, payload.init);
1247 _ = try c.addToken(.semicolon, ";");
1248
1249 return c.addNode(.{
1250 .tag = .simple_var_decl,
1251 .main_token = const_tok,
1252 .data = .{
1253 .lhs = 0,
1254 .rhs = init,
1255 },
1256 });
1257 },
1258 .static_local_var => {
1259 const payload = node.castTag(.static_local_var).?.data;
1260
1261 const const_tok = try c.addToken(.keyword_const, "const");
1262 _ = try c.addIdentifier(payload.name);
1263 _ = try c.addToken(.equal, "=");
1264
1265 const kind_tok = try c.addToken(.keyword_struct, "struct");
1266 _ = try c.addToken(.l_brace, "{");
1267
1268 const container_def = try c.addNode(.{
1269 .tag = .container_decl_two_trailing,
1270 .main_token = kind_tok,
1271 .data = .{
1272 .lhs = try renderNode(c, payload.init),
1273 .rhs = 0,
1274 },
1275 });
1276 _ = try c.addToken(.r_brace, "}");
1277 _ = try c.addToken(.semicolon, ";");
1278
1279 return c.addNode(.{
1280 .tag = .simple_var_decl,
1281 .main_token = const_tok,
1282 .data = .{
1283 .lhs = 0,
1284 .rhs = container_def,
1285 },
1286 });
1287 },
1288 .extern_local_var => {
1289 const payload = node.castTag(.extern_local_var).?.data;
1290
1291 const const_tok = try c.addToken(.keyword_const, "const");
1292 _ = try c.addIdentifier(payload.name);
1293 _ = try c.addToken(.equal, "=");
1294
1295 const kind_tok = try c.addToken(.keyword_struct, "struct");
1296 _ = try c.addToken(.l_brace, "{");
1297
1298 const container_def = try c.addNode(.{
1299 .tag = .container_decl_two_trailing,
1300 .main_token = kind_tok,
1301 .data = .{
1302 .lhs = try renderNode(c, payload.init),
1303 .rhs = 0,
1304 },
1305 });
1306 _ = try c.addToken(.r_brace, "}");
1307 _ = try c.addToken(.semicolon, ";");
1308
1309 return c.addNode(.{
1310 .tag = .simple_var_decl,
1311 .main_token = const_tok,
1312 .data = .{
1313 .lhs = 0,
1314 .rhs = container_def,
1315 },
1316 });
1317 },
1318 .mut_str => {
1319 const payload = node.castTag(.mut_str).?.data;
1320
1321 const var_tok = try c.addToken(.keyword_var, "var");
1322 _ = try c.addIdentifier(payload.name);
1323 _ = try c.addToken(.equal, "=");
1324
1325 const deref = try c.addNode(.{
1326 .tag = .deref,
1327 .data = .{
1328 .lhs = try renderNodeGrouped(c, payload.init),
1329 .rhs = undefined,
1330 },
1331 .main_token = try c.addToken(.period_asterisk, ".*"),
1332 });
1333 _ = try c.addToken(.semicolon, ";");
1334
1335 return c.addNode(.{
1336 .tag = .simple_var_decl,
1337 .main_token = var_tok,
1338 .data = .{ .lhs = 0, .rhs = deref },
1339 });
1340 },
1341 .var_decl => return renderVar(c, node),
1342 .arg_redecl, .alias => {
1343 const payload = @as(*Payload.ArgRedecl, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
1344 if (node.tag() == .alias) _ = try c.addToken(.keyword_pub, "pub");
1345 const mut_tok = if (node.tag() == .alias)
1346 try c.addToken(.keyword_const, "const")
1347 else
1348 try c.addToken(.keyword_var, "var");
1349 _ = try c.addIdentifier(payload.actual);
1350 _ = try c.addToken(.equal, "=");
1351
1352 const init = try c.addNode(.{
1353 .tag = .identifier,
1354 .main_token = try c.addIdentifier(payload.mangled),
1355 .data = undefined,
1356 });
1357 _ = try c.addToken(.semicolon, ";");
1358
1359 return c.addNode(.{
1360 .tag = .simple_var_decl,
1361 .main_token = mut_tok,
1362 .data = .{
1363 .lhs = 0,
1364 .rhs = init,
1365 },
1366 });
1367 },
1368 .int_cast => {
1369 const payload = node.castTag(.int_cast).?.data;
1370 return renderBuiltinCall(c, "@intCast", &.{payload});
1371 },
1372 .const_cast => {
1373 const payload = node.castTag(.const_cast).?.data;
1374 return renderBuiltinCall(c, "@constCast", &.{payload});
1375 },
1376 .volatile_cast => {
1377 const payload = node.castTag(.volatile_cast).?.data;
1378 return renderBuiltinCall(c, "@volatileCast", &.{payload});
1379 },
1380 .signed_remainder => {
1381 const payload = node.castTag(.signed_remainder).?.data;
1382 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "signedRemainder" });
1383 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
1384 },
1385 .div_trunc => {
1386 const payload = node.castTag(.div_trunc).?.data;
1387 return renderBuiltinCall(c, "@divTrunc", &.{ payload.lhs, payload.rhs });
1388 },
1389 .int_from_bool => {
1390 const payload = node.castTag(.int_from_bool).?.data;
1391 return renderBuiltinCall(c, "@intFromBool", &.{payload});
1392 },
1393 .as => {
1394 const payload = node.castTag(.as).?.data;
1395 return renderBuiltinCall(c, "@as", &.{ payload.lhs, payload.rhs });
1396 },
1397 .truncate => {
1398 const payload = node.castTag(.truncate).?.data;
1399 return renderBuiltinCall(c, "@truncate", &.{payload});
1400 },
1401 .bit_cast => {
1402 const payload = node.castTag(.bit_cast).?.data;
1403 return renderBuiltinCall(c, "@bitCast", &.{payload});
1404 },
1405 .float_cast => {
1406 const payload = node.castTag(.float_cast).?.data;
1407 return renderBuiltinCall(c, "@floatCast", &.{payload});
1408 },
1409 .int_from_float => {
1410 const payload = node.castTag(.int_from_float).?.data;
1411 return renderBuiltinCall(c, "@intFromFloat", &.{payload});
1412 },
1413 .float_from_int => {
1414 const payload = node.castTag(.float_from_int).?.data;
1415 return renderBuiltinCall(c, "@floatFromInt", &.{payload});
1416 },
1417 .ptr_from_int => {
1418 const payload = node.castTag(.ptr_from_int).?.data;
1419 return renderBuiltinCall(c, "@ptrFromInt", &.{payload});
1420 },
1421 .int_from_ptr => {
1422 const payload = node.castTag(.int_from_ptr).?.data;
1423 return renderBuiltinCall(c, "@intFromPtr", &.{payload});
1424 },
1425 .align_cast => {
1426 const payload = node.castTag(.align_cast).?.data;
1427 return renderBuiltinCall(c, "@alignCast", &.{payload});
1428 },
1429 .ptr_cast => {
1430 const payload = node.castTag(.ptr_cast).?.data;
1431 return renderBuiltinCall(c, "@ptrCast", &.{payload});
1432 },
1433 .div_exact => {
1434 const payload = node.castTag(.div_exact).?.data;
1435 return renderBuiltinCall(c, "@divExact", &.{ payload.lhs, payload.rhs });
1436 },
1437 .offset_of => {
1438 const payload = node.castTag(.offset_of).?.data;
1439 return renderBuiltinCall(c, "@offsetOf", &.{ payload.lhs, payload.rhs });
1440 },
1441 .sizeof => {
1442 const payload = node.castTag(.sizeof).?.data;
1443 return renderBuiltinCall(c, "@sizeOf", &.{payload});
1444 },
1445 .shuffle => {
1446 const payload = node.castTag(.shuffle).?.data;
1447 return renderBuiltinCall(c, "@shuffle", &.{
1448 payload.element_type,
1449 payload.a,
1450 payload.b,
1451 payload.mask_vector,
1452 });
1453 },
1454 .builtin_extern => {
1455 const payload = node.castTag(.builtin_extern).?.data;
1456
1457 var info_inits: [1]Payload.ContainerInitDot.Initializer = .{
1458 .{ .name = "name", .value = payload.name },
1459 };
1460 var info_payload: Payload.ContainerInitDot = .{
1461 .base = .{ .tag = .container_init_dot },
1462 .data = &info_inits,
1463 };
1464
1465 return renderBuiltinCall(c, "@extern", &.{
1466 payload.type,
1467 .{ .ptr_otherwise = &info_payload.base },
1468 });
1469 },
1470 .macro_arithmetic => {
1471 const payload = node.castTag(.macro_arithmetic).?.data;
1472 const op = @tagName(payload.op);
1473 const import_node = try renderStdImport(c, &.{ "zig", "c_translation", "MacroArithmetic", op });
1474 return renderCall(c, import_node, &.{ payload.lhs, payload.rhs });
1475 },
1476 .alignof => {
1477 const payload = node.castTag(.alignof).?.data;
1478 return renderBuiltinCall(c, "@alignOf", &.{payload});
1479 },
1480 .typeof => {
1481 const payload = node.castTag(.typeof).?.data;
1482 return renderBuiltinCall(c, "@TypeOf", &.{payload});
1483 },
1484 .typeinfo => {
1485 const payload = node.castTag(.typeinfo).?.data;
1486 return renderBuiltinCall(c, "@typeInfo", &.{payload});
1487 },
1488 .negate => return renderPrefixOp(c, node, .negation, .minus, "-"),
1489 .negate_wrap => return renderPrefixOp(c, node, .negation_wrap, .minus_percent, "-%"),
1490 .bit_not => return renderPrefixOp(c, node, .bit_not, .tilde, "~"),
1491 .not => return renderPrefixOp(c, node, .bool_not, .bang, "!"),
1492 .optional_type => return renderPrefixOp(c, node, .optional_type, .question_mark, "?"),
1493 .address_of => {
1494 const payload = node.castTag(.address_of).?.data;
1495
1496 const ampersand = try c.addToken(.ampersand, "&");
1497 const base = if (payload.tag() == .fn_identifier)
1498 try c.addNode(.{
1499 .tag = .identifier,
1500 .main_token = try c.addIdentifier(payload.castTag(.fn_identifier).?.data),
1501 .data = undefined,
1502 })
1503 else
1504 try renderNodeGrouped(c, payload);
1505 return c.addNode(.{
1506 .tag = .address_of,
1507 .main_token = ampersand,
1508 .data = .{
1509 .lhs = base,
1510 .rhs = undefined,
1511 },
1512 });
1513 },
1514 .deref => {
1515 const payload = node.castTag(.deref).?.data;
1516 const operand = try renderNodeGrouped(c, payload);
1517 const deref_tok = try c.addToken(.period_asterisk, ".*");
1518 return c.addNode(.{
1519 .tag = .deref,
1520 .main_token = deref_tok,
1521 .data = .{
1522 .lhs = operand,
1523 .rhs = undefined,
1524 },
1525 });
1526 },
1527 .unwrap => {
1528 const payload = node.castTag(.unwrap).?.data;
1529 const operand = try renderNodeGrouped(c, payload);
1530 const period = try c.addToken(.period, ".");
1531 const question_mark = try c.addToken(.question_mark, "?");
1532 return c.addNode(.{
1533 .tag = .unwrap_optional,
1534 .main_token = period,
1535 .data = .{
1536 .lhs = operand,
1537 .rhs = question_mark,
1538 },
1539 });
1540 },
1541 .c_pointer, .single_pointer => {
1542 const payload = @as(*Payload.Pointer, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
1543
1544 const main_token = if (node.tag() == .single_pointer)
1545 try c.addToken(.asterisk, "*")
1546 else blk: {
1547 const res = try c.addToken(.l_bracket, "[");
1548 _ = try c.addToken(.asterisk, "*");
1549 _ = try c.addIdentifier("c");
1550 _ = try c.addToken(.r_bracket, "]");
1551 break :blk res;
1552 };
1553 if (payload.is_const) _ = try c.addToken(.keyword_const, "const");
1554 if (payload.is_volatile) _ = try c.addToken(.keyword_volatile, "volatile");
1555 const elem_type = try renderNodeGrouped(c, payload.elem_type);
1556
1557 return c.addNode(.{
1558 .tag = .ptr_type_aligned,
1559 .main_token = main_token,
1560 .data = .{
1561 .lhs = 0,
1562 .rhs = elem_type,
1563 },
1564 });
1565 },
1566 .add => return renderBinOpGrouped(c, node, .add, .plus, "+"),
1567 .add_assign => return renderBinOp(c, node, .assign_add, .plus_equal, "+="),
1568 .add_wrap => return renderBinOpGrouped(c, node, .add_wrap, .plus_percent, "+%"),
1569 .add_wrap_assign => return renderBinOp(c, node, .assign_add_wrap, .plus_percent_equal, "+%="),
1570 .sub => return renderBinOpGrouped(c, node, .sub, .minus, "-"),
1571 .sub_assign => return renderBinOp(c, node, .assign_sub, .minus_equal, "-="),
1572 .sub_wrap => return renderBinOpGrouped(c, node, .sub_wrap, .minus_percent, "-%"),
1573 .sub_wrap_assign => return renderBinOp(c, node, .assign_sub_wrap, .minus_percent_equal, "-%="),
1574 .mul => return renderBinOpGrouped(c, node, .mul, .asterisk, "*"),
1575 .mul_assign => return renderBinOp(c, node, .assign_mul, .asterisk_equal, "*="),
1576 .mul_wrap => return renderBinOpGrouped(c, node, .mul_wrap, .asterisk_percent, "*%"),
1577 .mul_wrap_assign => return renderBinOp(c, node, .assign_mul_wrap, .asterisk_percent_equal, "*%="),
1578 .div => return renderBinOpGrouped(c, node, .div, .slash, "/"),
1579 .div_assign => return renderBinOp(c, node, .assign_div, .slash_equal, "/="),
1580 .shl => return renderBinOpGrouped(c, node, .shl, .angle_bracket_angle_bracket_left, "<<"),
1581 .shl_assign => return renderBinOp(c, node, .assign_shl, .angle_bracket_angle_bracket_left_equal, "<<="),
1582 .shr => return renderBinOpGrouped(c, node, .shr, .angle_bracket_angle_bracket_right, ">>"),
1583 .shr_assign => return renderBinOp(c, node, .assign_shr, .angle_bracket_angle_bracket_right_equal, ">>="),
1584 .mod => return renderBinOpGrouped(c, node, .mod, .percent, "%"),
1585 .mod_assign => return renderBinOp(c, node, .assign_mod, .percent_equal, "%="),
1586 .@"and" => return renderBinOpGrouped(c, node, .bool_and, .keyword_and, "and"),
1587 .@"or" => return renderBinOpGrouped(c, node, .bool_or, .keyword_or, "or"),
1588 .less_than => return renderBinOpGrouped(c, node, .less_than, .angle_bracket_left, "<"),
1589 .less_than_equal => return renderBinOpGrouped(c, node, .less_or_equal, .angle_bracket_left_equal, "<="),
1590 .greater_than => return renderBinOpGrouped(c, node, .greater_than, .angle_bracket_right, ">="),
1591 .greater_than_equal => return renderBinOpGrouped(c, node, .greater_or_equal, .angle_bracket_right_equal, ">="),
1592 .equal => return renderBinOpGrouped(c, node, .equal_equal, .equal_equal, "=="),
1593 .not_equal => return renderBinOpGrouped(c, node, .bang_equal, .bang_equal, "!="),
1594 .bit_and => return renderBinOpGrouped(c, node, .bit_and, .ampersand, "&"),
1595 .bit_and_assign => return renderBinOp(c, node, .assign_bit_and, .ampersand_equal, "&="),
1596 .bit_or => return renderBinOpGrouped(c, node, .bit_or, .pipe, "|"),
1597 .bit_or_assign => return renderBinOp(c, node, .assign_bit_or, .pipe_equal, "|="),
1598 .bit_xor => return renderBinOpGrouped(c, node, .bit_xor, .caret, "^"),
1599 .bit_xor_assign => return renderBinOp(c, node, .assign_bit_xor, .caret_equal, "^="),
1600 .array_cat => return renderBinOp(c, node, .array_cat, .plus_plus, "++"),
1601 .ellipsis3 => return renderBinOpGrouped(c, node, .switch_range, .ellipsis3, "..."),
1602 .assign => return renderBinOp(c, node, .assign, .equal, "="),
1603 .empty_block => {
1604 const l_brace = try c.addToken(.l_brace, "{");
1605 _ = try c.addToken(.r_brace, "}");
1606 return c.addNode(.{
1607 .tag = .block_two,
1608 .main_token = l_brace,
1609 .data = .{
1610 .lhs = 0,
1611 .rhs = 0,
1612 },
1613 });
1614 },
1615 .block_single => {
1616 const payload = node.castTag(.block_single).?.data;
1617 const l_brace = try c.addToken(.l_brace, "{");
1618
1619 const stmt = try renderNode(c, payload);
1620 try addSemicolonIfNeeded(c, payload);
1621
1622 _ = try c.addToken(.r_brace, "}");
1623 return c.addNode(.{
1624 .tag = .block_two_semicolon,
1625 .main_token = l_brace,
1626 .data = .{
1627 .lhs = stmt,
1628 .rhs = 0,
1629 },
1630 });
1631 },
1632 .block => {
1633 const payload = node.castTag(.block).?.data;
1634 if (payload.label) |some| {
1635 _ = try c.addIdentifier(some);
1636 _ = try c.addToken(.colon, ":");
1637 }
1638 const l_brace = try c.addToken(.l_brace, "{");
1639
1640 var stmts = std.ArrayList(NodeIndex).init(c.gpa);
1641 defer stmts.deinit();
1642 for (payload.stmts) |stmt| {
1643 const res = try renderNode(c, stmt);
1644 if (res == 0) continue;
1645 try addSemicolonIfNeeded(c, stmt);
1646 try stmts.append(res);
1647 }
1648 const span = try c.listToSpan(stmts.items);
1649 _ = try c.addToken(.r_brace, "}");
1650
1651 const semicolon = c.tokens.items(.tag)[c.tokens.len - 2] == .semicolon;
1652 return c.addNode(.{
1653 .tag = if (semicolon) .block_semicolon else .block,
1654 .main_token = l_brace,
1655 .data = .{
1656 .lhs = span.start,
1657 .rhs = span.end,
1658 },
1659 });
1660 },
1661 .func => return renderFunc(c, node),
1662 .pub_inline_fn => return renderMacroFunc(c, node),
1663 .discard => {
1664 const payload = node.castTag(.discard).?.data;
1665 if (payload.should_skip) return @as(NodeIndex, 0);
1666
1667 const lhs = try c.addNode(.{
1668 .tag = .identifier,
1669 .main_token = try c.addToken(.identifier, "_"),
1670 .data = undefined,
1671 });
1672 const main_token = try c.addToken(.equal, "=");
1673 if (payload.value.tag() == .identifier) {
1674 // Render as `_ = &foo;` to avoid tripping "pointless discard" and "local variable never mutated" errors.
1675 var addr_of_pl: Payload.UnOp = .{
1676 .base = .{ .tag = .address_of },
1677 .data = payload.value,
1678 };
1679 const addr_of: Node = .{ .ptr_otherwise = &addr_of_pl.base };
1680 return c.addNode(.{
1681 .tag = .assign,
1682 .main_token = main_token,
1683 .data = .{
1684 .lhs = lhs,
1685 .rhs = try renderNode(c, addr_of),
1686 },
1687 });
1688 } else {
1689 return c.addNode(.{
1690 .tag = .assign,
1691 .main_token = main_token,
1692 .data = .{
1693 .lhs = lhs,
1694 .rhs = try renderNode(c, payload.value),
1695 },
1696 });
1697 }
1698 },
1699 .@"while" => {
1700 const payload = node.castTag(.@"while").?.data;
1701 const while_tok = try c.addToken(.keyword_while, "while");
1702 _ = try c.addToken(.l_paren, "(");
1703 const cond = try renderNode(c, payload.cond);
1704 _ = try c.addToken(.r_paren, ")");
1705
1706 const cont_expr = if (payload.cont_expr) |some| blk: {
1707 _ = try c.addToken(.colon, ":");
1708 _ = try c.addToken(.l_paren, "(");
1709 const res = try renderNode(c, some);
1710 _ = try c.addToken(.r_paren, ")");
1711 break :blk res;
1712 } else 0;
1713 const body = try renderNode(c, payload.body);
1714
1715 if (cont_expr == 0) {
1716 return c.addNode(.{
1717 .tag = .while_simple,
1718 .main_token = while_tok,
1719 .data = .{
1720 .lhs = cond,
1721 .rhs = body,
1722 },
1723 });
1724 } else {
1725 return c.addNode(.{
1726 .tag = .while_cont,
1727 .main_token = while_tok,
1728 .data = .{
1729 .lhs = cond,
1730 .rhs = try c.addExtra(std.zig.Ast.Node.WhileCont{
1731 .cont_expr = cont_expr,
1732 .then_expr = body,
1733 }),
1734 },
1735 });
1736 }
1737 },
1738 .while_true => {
1739 const payload = node.castTag(.while_true).?.data;
1740 const while_tok = try c.addToken(.keyword_while, "while");
1741 _ = try c.addToken(.l_paren, "(");
1742 const cond = try c.addNode(.{
1743 .tag = .identifier,
1744 .main_token = try c.addToken(.identifier, "true"),
1745 .data = undefined,
1746 });
1747 _ = try c.addToken(.r_paren, ")");
1748 const body = try renderNode(c, payload);
1749
1750 return c.addNode(.{
1751 .tag = .while_simple,
1752 .main_token = while_tok,
1753 .data = .{
1754 .lhs = cond,
1755 .rhs = body,
1756 },
1757 });
1758 },
1759 .@"if" => {
1760 const payload = node.castTag(.@"if").?.data;
1761 const if_tok = try c.addToken(.keyword_if, "if");
1762 _ = try c.addToken(.l_paren, "(");
1763 const cond = try renderNode(c, payload.cond);
1764 _ = try c.addToken(.r_paren, ")");
1765
1766 const then_expr = try renderNode(c, payload.then);
1767 const else_node = payload.@"else" orelse return c.addNode(.{
1768 .tag = .if_simple,
1769 .main_token = if_tok,
1770 .data = .{
1771 .lhs = cond,
1772 .rhs = then_expr,
1773 },
1774 });
1775 _ = try c.addToken(.keyword_else, "else");
1776 const else_expr = try renderNode(c, else_node);
1777
1778 return c.addNode(.{
1779 .tag = .@"if",
1780 .main_token = if_tok,
1781 .data = .{
1782 .lhs = cond,
1783 .rhs = try c.addExtra(std.zig.Ast.Node.If{
1784 .then_expr = then_expr,
1785 .else_expr = else_expr,
1786 }),
1787 },
1788 });
1789 },
1790 .if_not_break => {
1791 const payload = node.castTag(.if_not_break).?.data;
1792 const if_tok = try c.addToken(.keyword_if, "if");
1793 _ = try c.addToken(.l_paren, "(");
1794 const cond = try c.addNode(.{
1795 .tag = .bool_not,
1796 .main_token = try c.addToken(.bang, "!"),
1797 .data = .{
1798 .lhs = try renderNodeGrouped(c, payload),
1799 .rhs = undefined,
1800 },
1801 });
1802 _ = try c.addToken(.r_paren, ")");
1803 const then_expr = try c.addNode(.{
1804 .tag = .@"break",
1805 .main_token = try c.addToken(.keyword_break, "break"),
1806 .data = .{
1807 .lhs = 0,
1808 .rhs = 0,
1809 },
1810 });
1811
1812 return c.addNode(.{
1813 .tag = .if_simple,
1814 .main_token = if_tok,
1815 .data = .{
1816 .lhs = cond,
1817 .rhs = then_expr,
1818 },
1819 });
1820 },
1821 .@"switch" => {
1822 const payload = node.castTag(.@"switch").?.data;
1823 const switch_tok = try c.addToken(.keyword_switch, "switch");
1824 _ = try c.addToken(.l_paren, "(");
1825 const cond = try renderNode(c, payload.cond);
1826 _ = try c.addToken(.r_paren, ")");
1827
1828 _ = try c.addToken(.l_brace, "{");
1829 var cases = try c.gpa.alloc(NodeIndex, payload.cases.len);
1830 defer c.gpa.free(cases);
1831 for (payload.cases, 0..) |case, i| {
1832 cases[i] = try renderNode(c, case);
1833 _ = try c.addToken(.comma, ",");
1834 }
1835 const span = try c.listToSpan(cases);
1836 _ = try c.addToken(.r_brace, "}");
1837 return c.addNode(.{
1838 .tag = .switch_comma,
1839 .main_token = switch_tok,
1840 .data = .{
1841 .lhs = cond,
1842 .rhs = try c.addExtra(NodeSubRange{
1843 .start = span.start,
1844 .end = span.end,
1845 }),
1846 },
1847 });
1848 },
1849 .switch_else => {
1850 const payload = node.castTag(.switch_else).?.data;
1851 _ = try c.addToken(.keyword_else, "else");
1852 return c.addNode(.{
1853 .tag = .switch_case_one,
1854 .main_token = try c.addToken(.equal_angle_bracket_right, "=>"),
1855 .data = .{
1856 .lhs = 0,
1857 .rhs = try renderNode(c, payload),
1858 },
1859 });
1860 },
1861 .switch_prong => {
1862 const payload = node.castTag(.switch_prong).?.data;
1863 var items = try c.gpa.alloc(NodeIndex, @max(payload.cases.len, 1));
1864 defer c.gpa.free(items);
1865 items[0] = 0;
1866 for (payload.cases, 0..) |item, i| {
1867 if (i != 0) _ = try c.addToken(.comma, ",");
1868 items[i] = try renderNode(c, item);
1869 }
1870 _ = try c.addToken(.r_brace, "}");
1871 if (items.len < 2) {
1872 return c.addNode(.{
1873 .tag = .switch_case_one,
1874 .main_token = try c.addToken(.equal_angle_bracket_right, "=>"),
1875 .data = .{
1876 .lhs = items[0],
1877 .rhs = try renderNode(c, payload.cond),
1878 },
1879 });
1880 } else {
1881 const span = try c.listToSpan(items);
1882 return c.addNode(.{
1883 .tag = .switch_case,
1884 .main_token = try c.addToken(.equal_angle_bracket_right, "=>"),
1885 .data = .{
1886 .lhs = try c.addExtra(NodeSubRange{
1887 .start = span.start,
1888 .end = span.end,
1889 }),
1890 .rhs = try renderNode(c, payload.cond),
1891 },
1892 });
1893 }
1894 },
1895 .opaque_literal => {
1896 const opaque_tok = try c.addToken(.keyword_opaque, "opaque");
1897 _ = try c.addToken(.l_brace, "{");
1898 _ = try c.addToken(.r_brace, "}");
1899
1900 return c.addNode(.{
1901 .tag = .container_decl_two,
1902 .main_token = opaque_tok,
1903 .data = .{
1904 .lhs = 0,
1905 .rhs = 0,
1906 },
1907 });
1908 },
1909 .array_access => {
1910 const payload = node.castTag(.array_access).?.data;
1911 const lhs = try renderNodeGrouped(c, payload.lhs);
1912 const l_bracket = try c.addToken(.l_bracket, "[");
1913 const index_expr = try renderNode(c, payload.rhs);
1914 _ = try c.addToken(.r_bracket, "]");
1915 return c.addNode(.{
1916 .tag = .array_access,
1917 .main_token = l_bracket,
1918 .data = .{
1919 .lhs = lhs,
1920 .rhs = index_expr,
1921 },
1922 });
1923 },
1924 .array_type => {
1925 const payload = node.castTag(.array_type).?.data;
1926 return renderArrayType(c, payload.len, payload.elem_type);
1927 },
1928 .null_sentinel_array_type => {
1929 const payload = node.castTag(.null_sentinel_array_type).?.data;
1930 return renderNullSentinelArrayType(c, payload.len, payload.elem_type);
1931 },
1932 .array_filler => {
1933 const payload = node.castTag(.array_filler).?.data;
1934
1935 const type_expr = try renderArrayType(c, 1, payload.type);
1936 const l_brace = try c.addToken(.l_brace, "{");
1937 const val = try renderNode(c, payload.filler);
1938 _ = try c.addToken(.r_brace, "}");
1939
1940 const init = try c.addNode(.{
1941 .tag = .array_init_one,
1942 .main_token = l_brace,
1943 .data = .{
1944 .lhs = type_expr,
1945 .rhs = val,
1946 },
1947 });
1948 return c.addNode(.{
1949 .tag = .array_cat,
1950 .main_token = try c.addToken(.asterisk_asterisk, "**"),
1951 .data = .{
1952 .lhs = init,
1953 .rhs = try c.addNode(.{
1954 .tag = .number_literal,
1955 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{payload.count}),
1956 .data = undefined,
1957 }),
1958 },
1959 });
1960 },
1961 .empty_array => {
1962 const payload = node.castTag(.empty_array).?.data;
1963
1964 const type_expr = try renderArrayType(c, 0, payload);
1965 return renderArrayInit(c, type_expr, &.{});
1966 },
1967 .array_init => {
1968 const payload = node.castTag(.array_init).?.data;
1969 const type_expr = try renderNode(c, payload.cond);
1970 return renderArrayInit(c, type_expr, payload.cases);
1971 },
1972 .vector_zero_init => {
1973 const payload = node.castTag(.vector_zero_init).?.data;
1974 return renderBuiltinCall(c, "@splat", &.{payload});
1975 },
1976 .field_access => {
1977 const payload = node.castTag(.field_access).?.data;
1978 const lhs = try renderNodeGrouped(c, payload.lhs);
1979 return renderFieldAccess(c, lhs, payload.field_name);
1980 },
1981 .@"struct", .@"union" => return renderRecord(c, node),
1982 .enum_constant => {
1983 const payload = node.castTag(.enum_constant).?.data;
1984
1985 if (payload.is_public) _ = try c.addToken(.keyword_pub, "pub");
1986 const const_tok = try c.addToken(.keyword_const, "const");
1987 _ = try c.addIdentifier(payload.name);
1988
1989 const type_node = if (payload.type) |enum_const_type| blk: {
1990 _ = try c.addToken(.colon, ":");
1991 break :blk try renderNode(c, enum_const_type);
1992 } else 0;
1993
1994 _ = try c.addToken(.equal, "=");
1995
1996 const init_node = try renderNode(c, payload.value);
1997 _ = try c.addToken(.semicolon, ";");
1998
1999 return c.addNode(.{
2000 .tag = .simple_var_decl,
2001 .main_token = const_tok,
2002 .data = .{
2003 .lhs = type_node,
2004 .rhs = init_node,
2005 },
2006 });
2007 },
2008 .tuple => {
2009 const payload = node.castTag(.tuple).?.data;
2010 _ = try c.addToken(.period, ".");
2011 const l_brace = try c.addToken(.l_brace, "{");
2012 var inits = try c.gpa.alloc(NodeIndex, @max(payload.len, 2));
2013 defer c.gpa.free(inits);
2014 inits[0] = 0;
2015 inits[1] = 0;
2016 for (payload, 0..) |init, i| {
2017 if (i != 0) _ = try c.addToken(.comma, ",");
2018 inits[i] = try renderNode(c, init);
2019 }
2020 _ = try c.addToken(.r_brace, "}");
2021 if (payload.len < 3) {
2022 return c.addNode(.{
2023 .tag = .array_init_dot_two,
2024 .main_token = l_brace,
2025 .data = .{
2026 .lhs = inits[0],
2027 .rhs = inits[1],
2028 },
2029 });
2030 } else {
2031 const span = try c.listToSpan(inits);
2032 return c.addNode(.{
2033 .tag = .array_init_dot,
2034 .main_token = l_brace,
2035 .data = .{
2036 .lhs = span.start,
2037 .rhs = span.end,
2038 },
2039 });
2040 }
2041 },
2042 .container_init_dot => {
2043 const payload = node.castTag(.container_init_dot).?.data;
2044 _ = try c.addToken(.period, ".");
2045 const l_brace = try c.addToken(.l_brace, "{");
2046 var inits = try c.gpa.alloc(NodeIndex, @max(payload.len, 2));
2047 defer c.gpa.free(inits);
2048 inits[0] = 0;
2049 inits[1] = 0;
2050 for (payload, 0..) |init, i| {
2051 _ = try c.addToken(.period, ".");
2052 _ = try c.addIdentifier(init.name);
2053 _ = try c.addToken(.equal, "=");
2054 inits[i] = try renderNode(c, init.value);
2055 _ = try c.addToken(.comma, ",");
2056 }
2057 _ = try c.addToken(.r_brace, "}");
2058
2059 if (payload.len < 3) {
2060 return c.addNode(.{
2061 .tag = .struct_init_dot_two_comma,
2062 .main_token = l_brace,
2063 .data = .{
2064 .lhs = inits[0],
2065 .rhs = inits[1],
2066 },
2067 });
2068 } else {
2069 const span = try c.listToSpan(inits);
2070 return c.addNode(.{
2071 .tag = .struct_init_dot_comma,
2072 .main_token = l_brace,
2073 .data = .{
2074 .lhs = span.start,
2075 .rhs = span.end,
2076 },
2077 });
2078 }
2079 },
2080 .container_init => {
2081 const payload = node.castTag(.container_init).?.data;
2082 const lhs = try renderNode(c, payload.lhs);
2083
2084 const l_brace = try c.addToken(.l_brace, "{");
2085 var inits = try c.gpa.alloc(NodeIndex, @max(payload.inits.len, 1));
2086 defer c.gpa.free(inits);
2087 inits[0] = 0;
2088 for (payload.inits, 0..) |init, i| {
2089 _ = try c.addToken(.period, ".");
2090 _ = try c.addIdentifier(init.name);
2091 _ = try c.addToken(.equal, "=");
2092 inits[i] = try renderNode(c, init.value);
2093 _ = try c.addToken(.comma, ",");
2094 }
2095 _ = try c.addToken(.r_brace, "}");
2096
2097 return switch (payload.inits.len) {
2098 0 => c.addNode(.{
2099 .tag = .struct_init_one,
2100 .main_token = l_brace,
2101 .data = .{
2102 .lhs = lhs,
2103 .rhs = 0,
2104 },
2105 }),
2106 1 => c.addNode(.{
2107 .tag = .struct_init_one_comma,
2108 .main_token = l_brace,
2109 .data = .{
2110 .lhs = lhs,
2111 .rhs = inits[0],
2112 },
2113 }),
2114 else => blk: {
2115 const span = try c.listToSpan(inits);
2116 break :blk c.addNode(.{
2117 .tag = .struct_init_comma,
2118 .main_token = l_brace,
2119 .data = .{
2120 .lhs = lhs,
2121 .rhs = try c.addExtra(NodeSubRange{
2122 .start = span.start,
2123 .end = span.end,
2124 }),
2125 },
2126 });
2127 },
2128 };
2129 },
2130 .@"anytype" => unreachable, // Handled in renderParams
2131 }
2132}
2133
2134fn renderRecord(c: *Context, node: Node) !NodeIndex {
2135 const payload = @as(*Payload.Record, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
2136 if (payload.layout == .@"packed")
2137 _ = try c.addToken(.keyword_packed, "packed")
2138 else if (payload.layout == .@"extern")
2139 _ = try c.addToken(.keyword_extern, "extern");
2140 const kind_tok = if (node.tag() == .@"struct")
2141 try c.addToken(.keyword_struct, "struct")
2142 else
2143 try c.addToken(.keyword_union, "union");
2144
2145 _ = try c.addToken(.l_brace, "{");
2146
2147 const num_vars = payload.variables.len;
2148 const num_funcs = payload.functions.len;
2149 const total_members = payload.fields.len + num_vars + num_funcs;
2150 const members = try c.gpa.alloc(NodeIndex, @max(total_members, 2));
2151 defer c.gpa.free(members);
2152 members[0] = 0;
2153 members[1] = 0;
2154
2155 for (payload.fields, 0..) |field, i| {
2156 const name_tok = try c.addTokenFmt(.identifier, "{p}", .{std.zig.fmtId(field.name)});
2157 _ = try c.addToken(.colon, ":");
2158 const type_expr = try renderNode(c, field.type);
2159
2160 const align_expr = if (field.alignment) |alignment| blk: {
2161 _ = try c.addToken(.keyword_align, "align");
2162 _ = try c.addToken(.l_paren, "(");
2163 const align_expr = try c.addNode(.{
2164 .tag = .number_literal,
2165 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{alignment}),
2166 .data = undefined,
2167 });
2168 _ = try c.addToken(.r_paren, ")");
2169 break :blk align_expr;
2170 } else 0;
2171
2172 const value_expr = if (field.default_value) |value| blk: {
2173 _ = try c.addToken(.equal, "=");
2174 break :blk try renderNode(c, value);
2175 } else 0;
2176
2177 members[i] = try c.addNode(if (align_expr == 0) .{
2178 .tag = .container_field_init,
2179 .main_token = name_tok,
2180 .data = .{
2181 .lhs = type_expr,
2182 .rhs = value_expr,
2183 },
2184 } else if (value_expr == 0) .{
2185 .tag = .container_field_align,
2186 .main_token = name_tok,
2187 .data = .{
2188 .lhs = type_expr,
2189 .rhs = align_expr,
2190 },
2191 } else .{
2192 .tag = .container_field,
2193 .main_token = name_tok,
2194 .data = .{
2195 .lhs = type_expr,
2196 .rhs = try c.addExtra(std.zig.Ast.Node.ContainerField{
2197 .align_expr = align_expr,
2198 .value_expr = value_expr,
2199 }),
2200 },
2201 });
2202 _ = try c.addToken(.comma, ",");
2203 }
2204 for (payload.variables, 0..) |variable, i| {
2205 members[payload.fields.len + i] = try renderNode(c, variable);
2206 }
2207 for (payload.functions, 0..) |function, i| {
2208 members[payload.fields.len + num_vars + i] = try renderNode(c, function);
2209 }
2210 _ = try c.addToken(.r_brace, "}");
2211
2212 if (total_members == 0) {
2213 return c.addNode(.{
2214 .tag = .container_decl_two,
2215 .main_token = kind_tok,
2216 .data = .{
2217 .lhs = 0,
2218 .rhs = 0,
2219 },
2220 });
2221 } else if (total_members <= 2) {
2222 return c.addNode(.{
2223 .tag = if (num_funcs == 0) .container_decl_two_trailing else .container_decl_two,
2224 .main_token = kind_tok,
2225 .data = .{
2226 .lhs = members[0],
2227 .rhs = members[1],
2228 },
2229 });
2230 } else {
2231 const span = try c.listToSpan(members);
2232 return c.addNode(.{
2233 .tag = if (num_funcs == 0) .container_decl_trailing else .container_decl,
2234 .main_token = kind_tok,
2235 .data = .{
2236 .lhs = span.start,
2237 .rhs = span.end,
2238 },
2239 });
2240 }
2241}
2242
2243fn renderFieldAccess(c: *Context, lhs: NodeIndex, field_name: []const u8) !NodeIndex {
2244 return c.addNode(.{
2245 .tag = .field_access,
2246 .main_token = try c.addToken(.period, "."),
2247 .data = .{
2248 .lhs = lhs,
2249 .rhs = try c.addTokenFmt(.identifier, "{p}", .{std.zig.fmtId(field_name)}),
2250 },
2251 });
2252}
2253
2254fn renderArrayInit(c: *Context, lhs: NodeIndex, inits: []const Node) !NodeIndex {
2255 const l_brace = try c.addToken(.l_brace, "{");
2256 var rendered = try c.gpa.alloc(NodeIndex, @max(inits.len, 1));
2257 defer c.gpa.free(rendered);
2258 rendered[0] = 0;
2259 for (inits, 0..) |init, i| {
2260 rendered[i] = try renderNode(c, init);
2261 _ = try c.addToken(.comma, ",");
2262 }
2263 _ = try c.addToken(.r_brace, "}");
2264 if (inits.len < 2) {
2265 return c.addNode(.{
2266 .tag = .array_init_one_comma,
2267 .main_token = l_brace,
2268 .data = .{
2269 .lhs = lhs,
2270 .rhs = rendered[0],
2271 },
2272 });
2273 } else {
2274 const span = try c.listToSpan(rendered);
2275 return c.addNode(.{
2276 .tag = .array_init_comma,
2277 .main_token = l_brace,
2278 .data = .{
2279 .lhs = lhs,
2280 .rhs = try c.addExtra(NodeSubRange{
2281 .start = span.start,
2282 .end = span.end,
2283 }),
2284 },
2285 });
2286 }
2287}
2288
2289fn renderArrayType(c: *Context, len: usize, elem_type: Node) !NodeIndex {
2290 const l_bracket = try c.addToken(.l_bracket, "[");
2291 const len_expr = try c.addNode(.{
2292 .tag = .number_literal,
2293 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{len}),
2294 .data = undefined,
2295 });
2296 _ = try c.addToken(.r_bracket, "]");
2297 const elem_type_expr = try renderNode(c, elem_type);
2298 return c.addNode(.{
2299 .tag = .array_type,
2300 .main_token = l_bracket,
2301 .data = .{
2302 .lhs = len_expr,
2303 .rhs = elem_type_expr,
2304 },
2305 });
2306}
2307
2308fn renderNullSentinelArrayType(c: *Context, len: usize, elem_type: Node) !NodeIndex {
2309 const l_bracket = try c.addToken(.l_bracket, "[");
2310 const len_expr = try c.addNode(.{
2311 .tag = .number_literal,
2312 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{len}),
2313 .data = undefined,
2314 });
2315 _ = try c.addToken(.colon, ":");
2316
2317 const sentinel_expr = try c.addNode(.{
2318 .tag = .number_literal,
2319 .main_token = try c.addToken(.number_literal, "0"),
2320 .data = undefined,
2321 });
2322
2323 _ = try c.addToken(.r_bracket, "]");
2324 const elem_type_expr = try renderNode(c, elem_type);
2325 return c.addNode(.{
2326 .tag = .array_type_sentinel,
2327 .main_token = l_bracket,
2328 .data = .{
2329 .lhs = len_expr,
2330 .rhs = try c.addExtra(std.zig.Ast.Node.ArrayTypeSentinel{
2331 .sentinel = sentinel_expr,
2332 .elem_type = elem_type_expr,
2333 }),
2334 },
2335 });
2336}
2337
2338fn addSemicolonIfNeeded(c: *Context, node: Node) !void {
2339 switch (node.tag()) {
2340 .warning => unreachable,
2341 .var_decl, .var_simple, .arg_redecl, .alias, .block, .empty_block, .block_single, .@"switch", .static_local_var, .extern_local_var, .mut_str => {},
2342 .while_true => {
2343 const payload = node.castTag(.while_true).?.data;
2344 return addSemicolonIfNotBlock(c, payload);
2345 },
2346 .@"while" => {
2347 const payload = node.castTag(.@"while").?.data;
2348 return addSemicolonIfNotBlock(c, payload.body);
2349 },
2350 .@"if" => {
2351 const payload = node.castTag(.@"if").?.data;
2352 if (payload.@"else") |some|
2353 return addSemicolonIfNeeded(c, some);
2354 return addSemicolonIfNotBlock(c, payload.then);
2355 },
2356 else => _ = try c.addToken(.semicolon, ";"),
2357 }
2358}
2359
2360fn addSemicolonIfNotBlock(c: *Context, node: Node) !void {
2361 switch (node.tag()) {
2362 .block, .empty_block, .block_single => {},
2363 else => _ = try c.addToken(.semicolon, ";"),
2364 }
2365}
2366
2367fn renderNodeGrouped(c: *Context, node: Node) !NodeIndex {
2368 switch (node.tag()) {
2369 .declaration => unreachable,
2370 .null_literal,
2371 .undefined_literal,
2372 .true_literal,
2373 .false_literal,
2374 .return_void,
2375 .zero_literal,
2376 .one_literal,
2377 .void_type,
2378 .noreturn_type,
2379 .@"anytype",
2380 .div_trunc,
2381 .signed_remainder,
2382 .int_cast,
2383 .const_cast,
2384 .volatile_cast,
2385 .as,
2386 .truncate,
2387 .bit_cast,
2388 .float_cast,
2389 .int_from_float,
2390 .float_from_int,
2391 .ptr_from_int,
2392 .std_mem_zeroes,
2393 .int_from_ptr,
2394 .sizeof,
2395 .alignof,
2396 .typeof,
2397 .typeinfo,
2398 .vector,
2399 .helpers_sizeof,
2400 .helpers_cast,
2401 .helpers_promoteIntLiteral,
2402 .helpers_shuffle_vector_index,
2403 .helpers_flexible_array_type,
2404 .std_mem_zeroinit,
2405 .integer_literal,
2406 .float_literal,
2407 .string_literal,
2408 .string_slice,
2409 .char_literal,
2410 .enum_literal,
2411 .identifier,
2412 .fn_identifier,
2413 .field_access,
2414 .ptr_cast,
2415 .type,
2416 .array_access,
2417 .align_cast,
2418 .optional_type,
2419 .c_pointer,
2420 .single_pointer,
2421 .unwrap,
2422 .deref,
2423 .not,
2424 .negate,
2425 .negate_wrap,
2426 .bit_not,
2427 .func,
2428 .call,
2429 .array_type,
2430 .null_sentinel_array_type,
2431 .int_from_bool,
2432 .div_exact,
2433 .offset_of,
2434 .shuffle,
2435 .builtin_extern,
2436 .static_local_var,
2437 .extern_local_var,
2438 .mut_str,
2439 .macro_arithmetic,
2440 => {
2441 // no grouping needed
2442 return renderNode(c, node);
2443 },
2444
2445 .opaque_literal,
2446 .empty_array,
2447 .block_single,
2448 .add,
2449 .add_wrap,
2450 .sub,
2451 .sub_wrap,
2452 .mul,
2453 .mul_wrap,
2454 .div,
2455 .shl,
2456 .shr,
2457 .mod,
2458 .@"and",
2459 .@"or",
2460 .less_than,
2461 .less_than_equal,
2462 .greater_than,
2463 .greater_than_equal,
2464 .equal,
2465 .not_equal,
2466 .bit_and,
2467 .bit_or,
2468 .bit_xor,
2469 .empty_block,
2470 .array_cat,
2471 .array_filler,
2472 .@"if",
2473 .@"struct",
2474 .@"union",
2475 .array_init,
2476 .vector_zero_init,
2477 .tuple,
2478 .container_init,
2479 .container_init_dot,
2480 .block,
2481 .address_of,
2482 => return c.addNode(.{
2483 .tag = .grouped_expression,
2484 .main_token = try c.addToken(.l_paren, "("),
2485 .data = .{
2486 .lhs = try renderNode(c, node),
2487 .rhs = try c.addToken(.r_paren, ")"),
2488 },
2489 }),
2490 .ellipsis3,
2491 .switch_prong,
2492 .warning,
2493 .var_decl,
2494 .fail_decl,
2495 .arg_redecl,
2496 .alias,
2497 .var_simple,
2498 .pub_var_simple,
2499 .enum_constant,
2500 .@"while",
2501 .@"switch",
2502 .@"break",
2503 .break_val,
2504 .pub_inline_fn,
2505 .discard,
2506 .@"continue",
2507 .@"return",
2508 .@"comptime",
2509 .@"defer",
2510 .asm_simple,
2511 .while_true,
2512 .if_not_break,
2513 .switch_else,
2514 .add_assign,
2515 .add_wrap_assign,
2516 .sub_assign,
2517 .sub_wrap_assign,
2518 .mul_assign,
2519 .mul_wrap_assign,
2520 .div_assign,
2521 .shl_assign,
2522 .shr_assign,
2523 .mod_assign,
2524 .bit_and_assign,
2525 .bit_or_assign,
2526 .bit_xor_assign,
2527 .assign,
2528 .helpers_macro,
2529 .import_c_builtin,
2530 => {
2531 // these should never appear in places where grouping might be needed.
2532 unreachable;
2533 },
2534 }
2535}
2536
2537fn renderPrefixOp(c: *Context, node: Node, tag: std.zig.Ast.Node.Tag, tok_tag: TokenTag, bytes: []const u8) !NodeIndex {
2538 const payload = @as(*Payload.UnOp, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
2539 return c.addNode(.{
2540 .tag = tag,
2541 .main_token = try c.addToken(tok_tag, bytes),
2542 .data = .{
2543 .lhs = try renderNodeGrouped(c, payload),
2544 .rhs = undefined,
2545 },
2546 });
2547}
2548
2549fn renderBinOpGrouped(c: *Context, node: Node, tag: std.zig.Ast.Node.Tag, tok_tag: TokenTag, bytes: []const u8) !NodeIndex {
2550 const payload = @as(*Payload.BinOp, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
2551 const lhs = try renderNodeGrouped(c, payload.lhs);
2552 return c.addNode(.{
2553 .tag = tag,
2554 .main_token = try c.addToken(tok_tag, bytes),
2555 .data = .{
2556 .lhs = lhs,
2557 .rhs = try renderNodeGrouped(c, payload.rhs),
2558 },
2559 });
2560}
2561
2562fn renderBinOp(c: *Context, node: Node, tag: std.zig.Ast.Node.Tag, tok_tag: TokenTag, bytes: []const u8) !NodeIndex {
2563 const payload = @as(*Payload.BinOp, @alignCast(@fieldParentPtr("base", node.ptr_otherwise))).data;
2564 const lhs = try renderNode(c, payload.lhs);
2565 return c.addNode(.{
2566 .tag = tag,
2567 .main_token = try c.addToken(tok_tag, bytes),
2568 .data = .{
2569 .lhs = lhs,
2570 .rhs = try renderNode(c, payload.rhs),
2571 },
2572 });
2573}
2574
2575fn renderStdImport(c: *Context, parts: []const []const u8) !NodeIndex {
2576 const import_tok = try c.addToken(.builtin, "@import");
2577 _ = try c.addToken(.l_paren, "(");
2578 const std_tok = try c.addToken(.string_literal, "\"std\"");
2579 const std_node = try c.addNode(.{
2580 .tag = .string_literal,
2581 .main_token = std_tok,
2582 .data = undefined,
2583 });
2584 _ = try c.addToken(.r_paren, ")");
2585
2586 const import_node = try c.addNode(.{
2587 .tag = .builtin_call_two,
2588 .main_token = import_tok,
2589 .data = .{
2590 .lhs = std_node,
2591 .rhs = 0,
2592 },
2593 });
2594
2595 var access_chain = import_node;
2596 for (parts) |part| {
2597 access_chain = try renderFieldAccess(c, access_chain, part);
2598 }
2599 return access_chain;
2600}
2601
2602fn renderCall(c: *Context, lhs: NodeIndex, args: []const Node) !NodeIndex {
2603 const lparen = try c.addToken(.l_paren, "(");
2604 const res = switch (args.len) {
2605 0 => try c.addNode(.{
2606 .tag = .call_one,
2607 .main_token = lparen,
2608 .data = .{
2609 .lhs = lhs,
2610 .rhs = 0,
2611 },
2612 }),
2613 1 => blk: {
2614 const arg = try renderNode(c, args[0]);
2615 break :blk try c.addNode(.{
2616 .tag = .call_one,
2617 .main_token = lparen,
2618 .data = .{
2619 .lhs = lhs,
2620 .rhs = arg,
2621 },
2622 });
2623 },
2624 else => blk: {
2625 var rendered = try c.gpa.alloc(NodeIndex, args.len);
2626 defer c.gpa.free(rendered);
2627
2628 for (args, 0..) |arg, i| {
2629 if (i != 0) _ = try c.addToken(.comma, ",");
2630 rendered[i] = try renderNode(c, arg);
2631 }
2632 const span = try c.listToSpan(rendered);
2633 break :blk try c.addNode(.{
2634 .tag = .call,
2635 .main_token = lparen,
2636 .data = .{
2637 .lhs = lhs,
2638 .rhs = try c.addExtra(NodeSubRange{
2639 .start = span.start,
2640 .end = span.end,
2641 }),
2642 },
2643 });
2644 },
2645 };
2646 _ = try c.addToken(.r_paren, ")");
2647 return res;
2648}
2649
2650fn renderBuiltinCall(c: *Context, builtin: []const u8, args: []const Node) !NodeIndex {
2651 const builtin_tok = try c.addToken(.builtin, builtin);
2652 _ = try c.addToken(.l_paren, "(");
2653 var arg_1: NodeIndex = 0;
2654 var arg_2: NodeIndex = 0;
2655 var arg_3: NodeIndex = 0;
2656 var arg_4: NodeIndex = 0;
2657 switch (args.len) {
2658 0 => {},
2659 1 => {
2660 arg_1 = try renderNode(c, args[0]);
2661 },
2662 2 => {
2663 arg_1 = try renderNode(c, args[0]);
2664 _ = try c.addToken(.comma, ",");
2665 arg_2 = try renderNode(c, args[1]);
2666 },
2667 4 => {
2668 arg_1 = try renderNode(c, args[0]);
2669 _ = try c.addToken(.comma, ",");
2670 arg_2 = try renderNode(c, args[1]);
2671 _ = try c.addToken(.comma, ",");
2672 arg_3 = try renderNode(c, args[2]);
2673 _ = try c.addToken(.comma, ",");
2674 arg_4 = try renderNode(c, args[3]);
2675 },
2676 else => unreachable, // expand this function as needed.
2677 }
2678
2679 _ = try c.addToken(.r_paren, ")");
2680 if (args.len <= 2) {
2681 return c.addNode(.{
2682 .tag = .builtin_call_two,
2683 .main_token = builtin_tok,
2684 .data = .{
2685 .lhs = arg_1,
2686 .rhs = arg_2,
2687 },
2688 });
2689 } else {
2690 std.debug.assert(args.len == 4);
2691
2692 const params = try c.listToSpan(&.{ arg_1, arg_2, arg_3, arg_4 });
2693 return c.addNode(.{
2694 .tag = .builtin_call,
2695 .main_token = builtin_tok,
2696 .data = .{
2697 .lhs = params.start,
2698 .rhs = params.end,
2699 },
2700 });
2701 }
2702}
2703
2704fn renderVar(c: *Context, node: Node) !NodeIndex {
2705 const payload = node.castTag(.var_decl).?.data;
2706 if (payload.is_pub) _ = try c.addToken(.keyword_pub, "pub");
2707 if (payload.is_extern) _ = try c.addToken(.keyword_extern, "extern");
2708 if (payload.is_export) _ = try c.addToken(.keyword_export, "export");
2709 if (payload.is_threadlocal) _ = try c.addToken(.keyword_threadlocal, "threadlocal");
2710 const mut_tok = if (payload.is_const)
2711 try c.addToken(.keyword_const, "const")
2712 else
2713 try c.addToken(.keyword_var, "var");
2714 _ = try c.addIdentifier(payload.name);
2715 _ = try c.addToken(.colon, ":");
2716 const type_node = try renderNode(c, payload.type);
2717
2718 const align_node = if (payload.alignment) |some| blk: {
2719 _ = try c.addToken(.keyword_align, "align");
2720 _ = try c.addToken(.l_paren, "(");
2721 const res = try c.addNode(.{
2722 .tag = .number_literal,
2723 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{some}),
2724 .data = undefined,
2725 });
2726 _ = try c.addToken(.r_paren, ")");
2727 break :blk res;
2728 } else 0;
2729
2730 const section_node = if (payload.linksection_string) |some| blk: {
2731 _ = try c.addToken(.keyword_linksection, "linksection");
2732 _ = try c.addToken(.l_paren, "(");
2733 const res = try c.addNode(.{
2734 .tag = .string_literal,
2735 .main_token = try c.addTokenFmt(.string_literal, "\"{}\"", .{std.zig.fmtEscapes(some)}),
2736 .data = undefined,
2737 });
2738 _ = try c.addToken(.r_paren, ")");
2739 break :blk res;
2740 } else 0;
2741
2742 const init_node = if (payload.init) |some| blk: {
2743 _ = try c.addToken(.equal, "=");
2744 break :blk try renderNode(c, some);
2745 } else 0;
2746 _ = try c.addToken(.semicolon, ";");
2747
2748 if (section_node == 0) {
2749 if (align_node == 0) {
2750 return c.addNode(.{
2751 .tag = .simple_var_decl,
2752 .main_token = mut_tok,
2753 .data = .{
2754 .lhs = type_node,
2755 .rhs = init_node,
2756 },
2757 });
2758 } else {
2759 return c.addNode(.{
2760 .tag = .local_var_decl,
2761 .main_token = mut_tok,
2762 .data = .{
2763 .lhs = try c.addExtra(std.zig.Ast.Node.LocalVarDecl{
2764 .type_node = type_node,
2765 .align_node = align_node,
2766 }),
2767 .rhs = init_node,
2768 },
2769 });
2770 }
2771 } else {
2772 return c.addNode(.{
2773 .tag = .global_var_decl,
2774 .main_token = mut_tok,
2775 .data = .{
2776 .lhs = try c.addExtra(std.zig.Ast.Node.GlobalVarDecl{
2777 .type_node = type_node,
2778 .align_node = align_node,
2779 .section_node = section_node,
2780 .addrspace_node = 0,
2781 }),
2782 .rhs = init_node,
2783 },
2784 });
2785 }
2786}
2787
2788fn renderFunc(c: *Context, node: Node) !NodeIndex {
2789 const payload = node.castTag(.func).?.data;
2790 if (payload.is_pub) _ = try c.addToken(.keyword_pub, "pub");
2791 if (payload.is_extern) _ = try c.addToken(.keyword_extern, "extern");
2792 if (payload.is_export) _ = try c.addToken(.keyword_export, "export");
2793 if (payload.is_inline) _ = try c.addToken(.keyword_inline, "inline");
2794 const fn_token = try c.addToken(.keyword_fn, "fn");
2795 if (payload.name) |some| _ = try c.addIdentifier(some);
2796
2797 const params = try renderParams(c, payload.params, payload.is_var_args);
2798 defer params.deinit();
2799 var span: NodeSubRange = undefined;
2800 if (params.items.len > 1) span = try c.listToSpan(params.items);
2801
2802 const align_expr = if (payload.alignment) |some| blk: {
2803 _ = try c.addToken(.keyword_align, "align");
2804 _ = try c.addToken(.l_paren, "(");
2805 const res = try c.addNode(.{
2806 .tag = .number_literal,
2807 .main_token = try c.addTokenFmt(.number_literal, "{d}", .{some}),
2808 .data = undefined,
2809 });
2810 _ = try c.addToken(.r_paren, ")");
2811 break :blk res;
2812 } else 0;
2813
2814 const section_expr = if (payload.linksection_string) |some| blk: {
2815 _ = try c.addToken(.keyword_linksection, "linksection");
2816 _ = try c.addToken(.l_paren, "(");
2817 const res = try c.addNode(.{
2818 .tag = .string_literal,
2819 .main_token = try c.addTokenFmt(.string_literal, "\"{}\"", .{std.zig.fmtEscapes(some)}),
2820 .data = undefined,
2821 });
2822 _ = try c.addToken(.r_paren, ")");
2823 break :blk res;
2824 } else 0;
2825
2826 const callconv_expr = if (payload.explicit_callconv) |some| blk: {
2827 _ = try c.addToken(.keyword_callconv, "callconv");
2828 _ = try c.addToken(.l_paren, "(");
2829 const cc_node = switch (some) {
2830 .c => cc_node: {
2831 _ = try c.addToken(.period, ".");
2832 break :cc_node try c.addNode(.{
2833 .tag = .enum_literal,
2834 .main_token = try c.addToken(.identifier, "c"),
2835 .data = undefined,
2836 });
2837 },
2838 .x86_64_sysv,
2839 .x86_64_win,
2840 .x86_stdcall,
2841 .x86_fastcall,
2842 .x86_thiscall,
2843 .x86_vectorcall,
2844 .aarch64_vfabi,
2845 .arm_aapcs,
2846 .arm_aapcs_vfp,
2847 .m68k_rtd,
2848 => cc_node: {
2849 // .{ .foo = .{} }
2850 _ = try c.addToken(.period, ".");
2851 const outer_lbrace = try c.addToken(.l_brace, "{");
2852 _ = try c.addToken(.period, ".");
2853 _ = try c.addToken(.identifier, @tagName(some));
2854 _ = try c.addToken(.equal, "=");
2855 _ = try c.addToken(.period, ".");
2856 const inner_lbrace = try c.addToken(.l_brace, "{");
2857 _ = try c.addToken(.r_brace, "}");
2858 _ = try c.addToken(.r_brace, "}");
2859 break :cc_node try c.addNode(.{
2860 .tag = .struct_init_dot_two,
2861 .main_token = outer_lbrace,
2862 .data = .{
2863 .lhs = try c.addNode(.{
2864 .tag = .struct_init_dot_two,
2865 .main_token = inner_lbrace,
2866 .data = .{ .lhs = 0, .rhs = 0 },
2867 }),
2868 .rhs = 0,
2869 },
2870 });
2871 },
2872 };
2873 _ = try c.addToken(.r_paren, ")");
2874 break :blk cc_node;
2875 } else 0;
2876
2877 const return_type_expr = try renderNode(c, payload.return_type);
2878
2879 const fn_proto = try blk: {
2880 if (align_expr == 0 and section_expr == 0 and callconv_expr == 0) {
2881 if (params.items.len < 2)
2882 break :blk c.addNode(.{
2883 .tag = .fn_proto_simple,
2884 .main_token = fn_token,
2885 .data = .{
2886 .lhs = params.items[0],
2887 .rhs = return_type_expr,
2888 },
2889 })
2890 else
2891 break :blk c.addNode(.{
2892 .tag = .fn_proto_multi,
2893 .main_token = fn_token,
2894 .data = .{
2895 .lhs = try c.addExtra(NodeSubRange{
2896 .start = span.start,
2897 .end = span.end,
2898 }),
2899 .rhs = return_type_expr,
2900 },
2901 });
2902 }
2903 if (params.items.len < 2)
2904 break :blk c.addNode(.{
2905 .tag = .fn_proto_one,
2906 .main_token = fn_token,
2907 .data = .{
2908 .lhs = try c.addExtra(std.zig.Ast.Node.FnProtoOne{
2909 .param = params.items[0],
2910 .align_expr = align_expr,
2911 .addrspace_expr = 0, // TODO
2912 .section_expr = section_expr,
2913 .callconv_expr = callconv_expr,
2914 }),
2915 .rhs = return_type_expr,
2916 },
2917 })
2918 else
2919 break :blk c.addNode(.{
2920 .tag = .fn_proto,
2921 .main_token = fn_token,
2922 .data = .{
2923 .lhs = try c.addExtra(std.zig.Ast.Node.FnProto{
2924 .params_start = span.start,
2925 .params_end = span.end,
2926 .align_expr = align_expr,
2927 .addrspace_expr = 0, // TODO
2928 .section_expr = section_expr,
2929 .callconv_expr = callconv_expr,
2930 }),
2931 .rhs = return_type_expr,
2932 },
2933 });
2934 };
2935
2936 const payload_body = payload.body orelse {
2937 if (payload.is_extern) {
2938 _ = try c.addToken(.semicolon, ";");
2939 }
2940 return fn_proto;
2941 };
2942 const body = try renderNode(c, payload_body);
2943 return c.addNode(.{
2944 .tag = .fn_decl,
2945 .main_token = fn_token,
2946 .data = .{
2947 .lhs = fn_proto,
2948 .rhs = body,
2949 },
2950 });
2951}
2952
2953fn renderMacroFunc(c: *Context, node: Node) !NodeIndex {
2954 const payload = node.castTag(.pub_inline_fn).?.data;
2955 _ = try c.addToken(.keyword_pub, "pub");
2956 _ = try c.addToken(.keyword_inline, "inline");
2957 const fn_token = try c.addToken(.keyword_fn, "fn");
2958 _ = try c.addIdentifier(payload.name);
2959
2960 const params = try renderParams(c, payload.params, false);
2961 defer params.deinit();
2962 var span: NodeSubRange = undefined;
2963 if (params.items.len > 1) span = try c.listToSpan(params.items);
2964
2965 const return_type_expr = try renderNodeGrouped(c, payload.return_type);
2966
2967 const fn_proto = blk: {
2968 if (params.items.len < 2) {
2969 break :blk try c.addNode(.{
2970 .tag = .fn_proto_simple,
2971 .main_token = fn_token,
2972 .data = .{
2973 .lhs = params.items[0],
2974 .rhs = return_type_expr,
2975 },
2976 });
2977 } else {
2978 break :blk try c.addNode(.{
2979 .tag = .fn_proto_multi,
2980 .main_token = fn_token,
2981 .data = .{
2982 .lhs = try c.addExtra(std.zig.Ast.Node.SubRange{
2983 .start = span.start,
2984 .end = span.end,
2985 }),
2986 .rhs = return_type_expr,
2987 },
2988 });
2989 }
2990 };
2991 return c.addNode(.{
2992 .tag = .fn_decl,
2993 .main_token = fn_token,
2994 .data = .{
2995 .lhs = fn_proto,
2996 .rhs = try renderNode(c, payload.body),
2997 },
2998 });
2999}
3000
3001fn renderParams(c: *Context, params: []Payload.Param, is_var_args: bool) !std.ArrayList(NodeIndex) {
3002 _ = try c.addToken(.l_paren, "(");
3003 var rendered = try std.ArrayList(NodeIndex).initCapacity(c.gpa, @max(params.len, 1));
3004 errdefer rendered.deinit();
3005
3006 for (params, 0..) |param, i| {
3007 if (i != 0) _ = try c.addToken(.comma, ",");
3008 if (param.is_noalias) _ = try c.addToken(.keyword_noalias, "noalias");
3009 if (param.name) |some| {
3010 _ = try c.addIdentifier(some);
3011 _ = try c.addToken(.colon, ":");
3012 }
3013 if (param.type.tag() == .@"anytype") {
3014 _ = try c.addToken(.keyword_anytype, "anytype");
3015 continue;
3016 }
3017 rendered.appendAssumeCapacity(try renderNode(c, param.type));
3018 }
3019 if (is_var_args) {
3020 if (params.len != 0) _ = try c.addToken(.comma, ",");
3021 _ = try c.addToken(.ellipsis3, "...");
3022 }
3023 _ = try c.addToken(.r_paren, ")");
3024
3025 if (rendered.items.len == 0) rendered.appendAssumeCapacity(0);
3026 return rendered;
3027}
test/cases/translate_c/_Static_assert.c deleted-7
...@@ -1,7 +0,0 @@
1_Static_assert(1 == 1, "");
2
3// translate-c
4// target=x86_64-linux
5// c_frontend=aro
6//
7// tmp.c:1:1: warning: ignoring _Static_assert declaration
test/cases/translate_c/atomic types.c deleted-8
...@@ -1,8 +0,0 @@
1typedef _Atomic(int) AtomicInt;
2
3// translate-c
4// target=x86_64-linux
5// c_frontend=aro
6//
7// tmp.c:1:22: warning: unsupported type: '_Atomic(int)'
8// pub const AtomicInt = @compileError("unable to resolve typedef child type");
test/cases/translate_c/empty declaration.c +2-2
...@@ -1,6 +1,6 @@...@@ -1,6 +1,6 @@
1;1;
22
3// translate-c3// translate-c
4// c_frontend=clang,aro4// c_frontend=clang
5//
5//6//
6//
\ No newline at end of file
test/cases/translate_c/enums.c+1-1
...@@ -6,7 +6,7 @@ enum Foo {...@@ -6,7 +6,7 @@ enum Foo {
66
7// translate-c7// translate-c
8// target=x86_64-linux8// target=x86_64-linux
9// c_frontend=clang,aro9// c_frontend=clang
10//10//
11// pub const FooA: c_int = 2;11// pub const FooA: c_int = 2;
12// pub const FooB: c_int = 5;12// pub const FooB: c_int = 5;
test/cases/translate_c/function prototype with parenthesis.c +1-1
...@@ -3,7 +3,7 @@ void ((f1)) (void *L);...@@ -3,7 +3,7 @@ void ((f1)) (void *L);
3void (((f2))) (void *L);3void (((f2))) (void *L);
44
5// translate-c5// translate-c
6// c_frontend=clang,aro6// c_frontend=clang
7//7//
8// pub extern fn f0(L: ?*anyopaque) void;8// pub extern fn f0(L: ?*anyopaque) void;
9// pub extern fn f1(L: ?*anyopaque) void;9// pub extern fn f1(L: ?*anyopaque) void;
test/cases/translate_c/large_packed_struct.c+1-1
...@@ -8,7 +8,7 @@ struct __attribute__((packed)) bar {...@@ -8,7 +8,7 @@ struct __attribute__((packed)) bar {
8};8};
99
10// translate-c10// translate-c
11// c_frontend=aro,clang11// c_frontend=clang
12//12//
13// pub const struct_bar = extern struct {13// pub const struct_bar = extern struct {
14// a: c_short align(1) = @import("std").mem.zeroes(c_short),14// a: c_short align(1) = @import("std").mem.zeroes(c_short),
test/cases/translate_c/noreturn attribute.c +1-1
...@@ -1,6 +1,6 @@...@@ -1,6 +1,6 @@
1void foo(void) __attribute__((noreturn));1void foo(void) __attribute__((noreturn));
22
3// translate-c3// translate-c
4// c_frontend=aro,clang4// c_frontend=clang
5//5//
6// pub extern fn foo() noreturn;6// pub extern fn foo() noreturn;
test/cases/translate_c/packed_union_nested_unpacked.c+1-1
...@@ -10,7 +10,7 @@ union Foo{...@@ -10,7 +10,7 @@ union Foo{
10} __attribute__((packed));10} __attribute__((packed));
1111
12// translate-c12// translate-c
13// c_frontend=aro,clang13// c_frontend=clang
14//14//
15// const struct_unnamed_1 = extern struct {15// const struct_unnamed_1 = extern struct {
16// b: c_int = @import("std").mem.zeroes(c_int),16// b: c_int = @import("std").mem.zeroes(c_int),
test/cases/translate_c/packed_union_simple.c+1-1
...@@ -4,7 +4,7 @@ union Foo {...@@ -4,7 +4,7 @@ union Foo {
4} __attribute__((packed));4} __attribute__((packed));
55
6// translate-c6// translate-c
7// c_frontend=aro,clang7// c_frontend=clang
8//8//
9// pub const union_Foo = extern union {9// pub const union_Foo = extern union {
10// x: c_short align(1),10// x: c_short align(1),
test/cases/translate_c/simple function prototypes.c +1-1
...@@ -2,7 +2,7 @@ void __attribute__((noreturn)) foo(void);...@@ -2,7 +2,7 @@ void __attribute__((noreturn)) foo(void);
2int bar(void);2int bar(void);
33
4// translate-c4// translate-c
5// c_frontend=clang,aro5// c_frontend=clang
6//6//
7// pub extern fn foo() noreturn;7// pub extern fn foo() noreturn;
8// pub extern fn bar() c_int;8// pub extern fn bar() c_int;
test/cases/translate_c/simple_struct.c+1-1
...@@ -3,7 +3,7 @@ struct Foo {...@@ -3,7 +3,7 @@ struct Foo {
3};3};
44
5// translate-c5// translate-c
6// c_frontend=aro,clang6// c_frontend=clang
7//7//
8// const struct_Foo = extern struct {8// const struct_Foo = extern struct {
9// x: c_int = @import("std").mem.zeroes(c_int),9// x: c_int = @import("std").mem.zeroes(c_int),
test/cases/translate_c/simple_union.c+1-1
...@@ -3,7 +3,7 @@ union Foo {...@@ -3,7 +3,7 @@ union Foo {
3};3};
44
5// translate-c5// translate-c
6// c_frontend=aro,clang6// c_frontend=clang
7//7//
8// pub const union_Foo = extern union {8// pub const union_Foo = extern union {
9// x: c_int,9// x: c_int,
test/cases/translate_c/struct prototype used in func.c +1-1
...@@ -2,7 +2,7 @@ struct Foo;...@@ -2,7 +2,7 @@ struct Foo;
2struct Foo *some_func(struct Foo *foo, int x);2struct Foo *some_func(struct Foo *foo, int x);
33
4// translate-c4// translate-c
5// c_frontend=clang,aro5// c_frontend=clang
6//6//
7// pub const struct_Foo = opaque {};7// pub const struct_Foo = opaque {};
8// pub extern fn some_func(foo: ?*struct_Foo, x: c_int) ?*struct_Foo;8// pub extern fn some_func(foo: ?*struct_Foo, x: c_int) ?*struct_Foo;
test/cases/translate_c/struct_with_aligned_fields.c+1-1
...@@ -3,7 +3,7 @@ struct foo {...@@ -3,7 +3,7 @@ struct foo {
3};3};
44
5// translate-c5// translate-c
6// c_frontend=aro,clang6// c_frontend=clang
7// 7//
8// pub const struct_foo = extern struct {8// pub const struct_foo = extern struct {
9// bar: c_short align(4) = @import("std").mem.zeroes(c_short),9// bar: c_short align(4) = @import("std").mem.zeroes(c_short),
test/cases/translate_c/struct_with_invalid_field_alignment.c deleted-35
...@@ -1,35 +0,0 @@
1// The aligned attribute cannot decrease the alignment of a field. The packed attribute is required
2// for decreasing the alignment. gcc and clang will compile these structs without error
3// (and possibly without warning), but checking the alignment will reveal a different value than
4// what was requested. This is consistent with the gcc documentation on type attributes.
5//
6// This test is currently broken for the clang frontend. See issue #19307.
7
8struct foo {
9 __attribute__((aligned(1)))int x;
10};
11
12struct bar {
13 __attribute__((aligned(2)))float y;
14};
15
16struct baz {
17 __attribute__((aligned(4)))double z;
18};
19
20// translate-c
21// c_frontend=aro
22// target=x86_64-linux
23//
24// pub const struct_foo = extern struct {
25// x: c_int = @import("std").mem.zeroes(c_int),
26// };
27//
28// pub const struct_bar = extern struct {
29// y: f32 = @import("std").mem.zeroes(f32),
30// };
31//
32// pub const struct_baz = extern struct {
33// z: f64 = @import("std").mem.zeroes(f64),
34// };
35//
test/cases/translate_c/type_referenced_struct.c+1-1
...@@ -8,7 +8,7 @@ struct Foo {...@@ -8,7 +8,7 @@ struct Foo {
8};8};
99
10// translate-c10// translate-c
11// c_frontend=aro,clang11// c_frontend=clang
12// target=x86_64-linux-gnu12// target=x86_64-linux-gnu
13//13//
14// pub const struct_Bar_1 = extern struct {14// pub const struct_Bar_1 = extern struct {
test/cases/translate_c/union_struct_forward_decl.c+1-1
...@@ -19,7 +19,7 @@ struct Foo {...@@ -19,7 +19,7 @@ struct Foo {
1919
2020
21// translate-c21// translate-c
22// c_frontend=aro,clang22// c_frontend=clang
23//23//
24// pub const struct_A = extern struct {24// pub const struct_A = extern struct {
25// x: c_short = @import("std").mem.zeroes(c_short),25// x: c_short = @import("std").mem.zeroes(c_short),
test/cases/translate_c/unnamed_fields_have_predictable_names.c+1-1
...@@ -6,7 +6,7 @@ struct b {...@@ -6,7 +6,7 @@ struct b {
6};6};
77
8// translate-c8// translate-c
9// c_frontend=aro,clang9// c_frontend=clang
10//10//
11// const struct_unnamed_1 = extern struct {11// const struct_unnamed_1 = extern struct {
12// x: c_int = @import("std").mem.zeroes(c_int),12// x: c_int = @import("std").mem.zeroes(c_int),
test/cases/translate_c/zero_width_field_alignment.c deleted-18
...@@ -1,18 +0,0 @@
1struct __attribute__((packed)) foo {
2 int x;
3 struct {};
4 float y;
5 union {};
6};
7
8// translate-c
9// c_frontend=aro
10//
11// const struct_unnamed_1 = extern struct {};
12// const union_unnamed_2 = extern union {};
13// pub const struct_foo = extern struct {
14// x: c_int align(1) = @import("std").mem.zeroes(c_int),
15// unnamed_0: struct_unnamed_1 align(1) = @import("std").mem.zeroes(struct_unnamed_1),
16// y: f32 align(1) = @import("std").mem.zeroes(f32),
17// unnamed_1: union_unnamed_2 align(1) = @import("std").mem.zeroes(union_unnamed_2),
18// };
test/cases/translate_c/zig_keywords_in_c_code.c+1-1
...@@ -3,7 +3,7 @@ struct comptime {...@@ -3,7 +3,7 @@ struct comptime {
3};3};
44
5// translate-c5// translate-c
6// c_frontend=aro,clang6// c_frontend=clang
7//7//
8// pub const struct_comptime = extern struct {8// pub const struct_comptime = extern struct {
9// @"defer": c_int = @import("std").mem.zeroes(c_int),9// @"defer": c_int = @import("std").mem.zeroes(c_int),
test/src/Cases.zig+20-36
...@@ -62,11 +62,6 @@ pub const Backend = enum {...@@ -62,11 +62,6 @@ pub const Backend = enum {
62 llvm,62 llvm,
63};63};
6464
65pub const CFrontend = enum {
66 clang,
67 aro,
68};
69
70/// A `Case` consists of a list of `Update`. The same `Compilation` is used for each65/// A `Case` consists of a list of `Update`. The same `Compilation` is used for each
71/// update, so each update's source is treated as a single file being66/// update, so each update's source is treated as a single file being
72/// updated by the test harness and incrementally compiled.67/// updated by the test harness and incrementally compiled.
...@@ -159,7 +154,6 @@ pub const Translate = struct {...@@ -159,7 +154,6 @@ pub const Translate = struct {
159 input: [:0]const u8,154 input: [:0]const u8,
160 target: std.Build.ResolvedTarget,155 target: std.Build.ResolvedTarget,
161 link_libc: bool,156 link_libc: bool,
162 c_frontend: CFrontend,
163 kind: union(enum) {157 kind: union(enum) {
164 /// Translate the input, run it and check that it158 /// Translate the input, run it and check that it
165 /// outputs the expected text.159 /// outputs the expected text.
...@@ -407,7 +401,6 @@ fn addFromDirInner(...@@ -407,7 +401,6 @@ fn addFromDirInner(
407401
408 const backends = try manifest.getConfigForKeyAlloc(ctx.arena, "backend", Backend);402 const backends = try manifest.getConfigForKeyAlloc(ctx.arena, "backend", Backend);
409 const targets = try manifest.getConfigForKeyAlloc(ctx.arena, "target", std.Target.Query);403 const targets = try manifest.getConfigForKeyAlloc(ctx.arena, "target", std.Target.Query);
410 const c_frontends = try manifest.getConfigForKeyAlloc(ctx.arena, "c_frontend", CFrontend);
411 const is_test = try manifest.getConfigForKeyAssertSingle("is_test", bool);404 const is_test = try manifest.getConfigForKeyAssertSingle("is_test", bool);
412 const link_libc = try manifest.getConfigForKeyAssertSingle("link_libc", bool);405 const link_libc = try manifest.getConfigForKeyAssertSingle("link_libc", bool);
413 const output_mode = try manifest.getConfigForKeyAssertSingle("output_mode", std.builtin.OutputMode);406 const output_mode = try manifest.getConfigForKeyAssertSingle("output_mode", std.builtin.OutputMode);
...@@ -416,34 +409,28 @@ fn addFromDirInner(...@@ -416,34 +409,28 @@ fn addFromDirInner(
416 const emit_bin = try manifest.getConfigForKeyAssertSingle("emit_bin", bool);409 const emit_bin = try manifest.getConfigForKeyAssertSingle("emit_bin", bool);
417410
418 if (manifest.type == .translate_c) {411 if (manifest.type == .translate_c) {
419 for (c_frontends) |c_frontend| {412 for (targets) |target_query| {
420 for (targets) |target_query| {413 const output = try manifest.trailingLinesSplit(ctx.arena);
421 const output = try manifest.trailingLinesSplit(ctx.arena);414 try ctx.translate.append(.{
422 try ctx.translate.append(.{415 .name = std.fs.path.stem(filename),
423 .name = std.fs.path.stem(filename),416 .target = b.resolveTargetQuery(target_query),
424 .c_frontend = c_frontend,417 .link_libc = link_libc,
425 .target = b.resolveTargetQuery(target_query),418 .input = src,
426 .link_libc = link_libc,419 .kind = .{ .translate = output },
427 .input = src,420 });
428 .kind = .{ .translate = output },
429 });
430 }
431 }421 }
432 continue;422 continue;
433 }423 }
434 if (manifest.type == .run_translated_c) {424 if (manifest.type == .run_translated_c) {
435 for (c_frontends) |c_frontend| {425 for (targets) |target_query| {
436 for (targets) |target_query| {426 const output = try manifest.trailingSplit(ctx.arena);
437 const output = try manifest.trailingSplit(ctx.arena);427 try ctx.translate.append(.{
438 try ctx.translate.append(.{428 .name = std.fs.path.stem(filename),
439 .name = std.fs.path.stem(filename),429 .target = b.resolveTargetQuery(target_query),
440 .c_frontend = c_frontend,430 .link_libc = link_libc,
441 .target = b.resolveTargetQuery(target_query),431 .input = src,
442 .link_libc = link_libc,432 .kind = .{ .run = output },
443 .input = src,433 });
444 .kind = .{ .run = output },
445 });
446 }
447 }434 }
448 continue;435 continue;
449 }436 }
...@@ -568,7 +555,7 @@ pub fn lowerToTranslateCSteps(...@@ -568,7 +555,7 @@ pub fn lowerToTranslateCSteps(
568 .optimize = .Debug,555 .optimize = .Debug,
569 .target = case.target,556 .target = case.target,
570 .link_libc = case.link_libc,557 .link_libc = case.link_libc,
571 .use_clang = case.c_frontend == .clang,558 .use_clang = true,
572 });559 });
573 translate_c.step.name = b.fmt("{s} translate-c", .{annotated_case_name});560 translate_c.step.name = b.fmt("{s} translate-c", .{annotated_case_name});
574561
...@@ -600,7 +587,7 @@ pub fn lowerToTranslateCSteps(...@@ -600,7 +587,7 @@ pub fn lowerToTranslateCSteps(
600 .optimize = .Debug,587 .optimize = .Debug,
601 .target = case.target,588 .target = case.target,
602 .link_libc = case.link_libc,589 .link_libc = case.link_libc,
603 .use_clang = case.c_frontend == .clang,590 .use_clang = true,
604 });591 });
605 translate_c.step.name = b.fmt("{s} translate-c", .{annotated_case_name});592 translate_c.step.name = b.fmt("{s} translate-c", .{annotated_case_name});
606593
...@@ -956,8 +943,6 @@ const TestManifestConfigDefaults = struct {...@@ -956,8 +943,6 @@ const TestManifestConfigDefaults = struct {
956 return "false";943 return "false";
957 } else if (std.mem.eql(u8, key, "link_libc")) {944 } else if (std.mem.eql(u8, key, "link_libc")) {
958 return "false";945 return "false";
959 } else if (std.mem.eql(u8, key, "c_frontend")) {
960 return "clang";
961 } else if (std.mem.eql(u8, key, "pic")) {946 } else if (std.mem.eql(u8, key, "pic")) {
962 return "null";947 return "null";
963 } else if (std.mem.eql(u8, key, "pie")) {948 } else if (std.mem.eql(u8, key, "pie")) {
...@@ -993,7 +978,6 @@ const TestManifest = struct {...@@ -993,7 +978,6 @@ const TestManifest = struct {
993 .{ "is_test", {} },978 .{ "is_test", {} },
994 .{ "output_mode", {} },979 .{ "output_mode", {} },
995 .{ "target", {} },980 .{ "target", {} },
996 .{ "c_frontend", {} },
997 .{ "link_libc", {} },981 .{ "link_libc", {} },
998 .{ "backend", {} },982 .{ "backend", {} },
999 .{ "pic", {} },983 .{ "pic", {} },