Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
self-hosted: generate zig IR for simple function
no tests for this yet. I think the quickest path to testing will be creating the .o files and linking with libc, executing, and then comparing output.
- Loading branch information
Showing
11 changed files
with
1,555 additions
and
315 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,96 @@ | ||
const std = @import("std"); | ||
const Allocator = mem.Allocator; | ||
const mem = std.mem; | ||
const ast = std.zig.ast; | ||
const Visib = @import("visib.zig").Visib; | ||
const ParsedFile = @import("parsed_file.zig").ParsedFile; | ||
const event = std.event; | ||
const Value = @import("value.zig").Value; | ||
const Token = std.zig.Token; | ||
const errmsg = @import("errmsg.zig"); | ||
const Scope = @import("scope.zig").Scope; | ||
const Module = @import("module.zig").Module; | ||
|
||
pub const Decl = struct { | ||
id: Id, | ||
name: []const u8, | ||
visib: Visib, | ||
resolution: event.Future(Module.BuildError!void), | ||
resolution_in_progress: u8, | ||
parsed_file: *ParsedFile, | ||
parent_scope: *Scope, | ||
|
||
pub const Table = std.HashMap([]const u8, *Decl, mem.hash_slice_u8, mem.eql_slice_u8); | ||
|
||
pub fn isExported(base: *const Decl, tree: *ast.Tree) bool { | ||
switch (base.id) { | ||
Id.Fn => { | ||
const fn_decl = @fieldParentPtr(Fn, "base", base); | ||
return fn_decl.isExported(tree); | ||
}, | ||
else => return false, | ||
} | ||
} | ||
|
||
pub fn getSpan(base: *const Decl) errmsg.Span { | ||
switch (base.id) { | ||
Id.Fn => { | ||
const fn_decl = @fieldParentPtr(Fn, "base", base); | ||
const fn_proto = fn_decl.fn_proto; | ||
const start = fn_proto.fn_token; | ||
const end = fn_proto.name_token orelse start; | ||
return errmsg.Span{ | ||
.first = start, | ||
.last = end + 1, | ||
}; | ||
}, | ||
else => @panic("TODO"), | ||
} | ||
} | ||
|
||
pub const Id = enum { | ||
Var, | ||
Fn, | ||
CompTime, | ||
}; | ||
|
||
pub const Var = struct { | ||
base: Decl, | ||
}; | ||
|
||
pub const Fn = struct { | ||
base: Decl, | ||
value: Val, | ||
fn_proto: *const ast.Node.FnProto, | ||
|
||
// TODO https://github.com/ziglang/zig/issues/683 and then make this anonymous | ||
pub const Val = union { | ||
Unresolved: void, | ||
Ok: *Value.Fn, | ||
}; | ||
|
||
pub fn externLibName(self: Fn, tree: *ast.Tree) ?[]const u8 { | ||
return if (self.fn_proto.extern_export_inline_token) |tok_index| x: { | ||
const token = tree.tokens.at(tok_index); | ||
break :x switch (token.id) { | ||
Token.Id.Extern => tree.tokenSlicePtr(token), | ||
else => null, | ||
}; | ||
} else null; | ||
} | ||
|
||
pub fn isExported(self: Fn, tree: *ast.Tree) bool { | ||
if (self.fn_proto.extern_export_inline_token) |tok_index| { | ||
const token = tree.tokens.at(tok_index); | ||
return token.id == Token.Id.Keyword_export; | ||
} else { | ||
return false; | ||
} | ||
} | ||
}; | ||
|
||
pub const CompTime = struct { | ||
base: Decl, | ||
}; | ||
}; | ||
|
Oops, something went wrong.