| 1 | //! JavaScript code generation backend |
| 2 | //! |
| 3 | //! * Air -(NodeGen)-> JsTree |
| 4 | //! * []JsTree -(Link)-> []const u8 |
| 5 | //! |
| 6 | pub const NodeGen = @import("NodeGen.zig"); |
| 7 | pub const Tree = @import("Tree.zig"); |
| 8 | pub const Link = @import("Link.zig"); |
| 9 | |
| 10 | codegen_map: std.AutoHashMapUnmanaged(Value, Tree) = .{}, |
| 11 | |
| 12 | pub fn deinit(backend: *Js, comp: *Comp) void { |
| 13 | { |
| 14 | var it = backend.codegen_map.valueIterator(); |
| 15 | while (it.next()) |item| { |
| 16 | item.deinit(comp.gpa); |
| 17 | } |
| 18 | } |
| 19 | |
| 20 | backend.codegen_map.deinit(comp.gpa); |
| 21 | } |
| 22 | |
| 23 | pub fn handleFunctionAir( |
| 24 | backend: *Js, |
| 25 | comp: *Comp, |
| 26 | value: Value, |
| 27 | air: Air, |
| 28 | arena: Allocator, |
| 29 | ) !u32 { |
| 30 | var ng = try NodeGen.init(comp.gpa, arena, &comp.intern_pool, air); |
| 31 | errdefer ng.deinit(); |
| 32 | try ng.build(); |
| 33 | |
| 34 | const tree = try ng.finalize(); |
| 35 | try backend.codegen_map.putNoClobber(comp.gpa, value, tree); |
| 36 | |
| 37 | return 0; |
| 38 | } |
| 39 | |
| 40 | pub fn link( |
| 41 | backend: *Js, |
| 42 | comp: *Comp, |
| 43 | entry_point: Comp.Decl.Index, |
| 44 | writer: std.io.AnyWriter, |
| 45 | ) !void { |
| 46 | var state: Link = .{ |
| 47 | .comp = comp, |
| 48 | .backend = backend, |
| 49 | }; |
| 50 | defer state.deinit(); |
| 51 | try state.linkJsCode(entry_point, writer); |
| 52 | } |
| 53 | |
| 54 | const Js = @This(); |
| 55 | |
| 56 | const std = @import("std"); |
| 57 | const assert = std.debug.assert; |
| 58 | const Allocator = std.mem.Allocator; |
| 59 | |
| 60 | const core = @import("../mod.zig"); |
| 61 | const Comp = core.Comp; |
| 62 | const Air = core.Air; |
| 63 | const InternPool = core.InternPool; |
| 64 | const Value = InternPool.Value; |