Merge pull request #155 from birth-software/comptime-for
First comptime for implementation
This commit is contained in:
commit
a38af3bbb6
File diff suppressed because it is too large
Load Diff
@ -625,7 +625,6 @@ const Analyzer = struct {
|
|||||||
.operator_switch_case => break,
|
.operator_switch_case => break,
|
||||||
else => {},
|
else => {},
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
break :blk switch (array_list.length) {
|
break :blk switch (array_list.length) {
|
||||||
@ -754,7 +753,7 @@ const Analyzer = struct {
|
|||||||
.operator_right_parenthesis, .operator_comma => Node.Index.null,
|
.operator_right_parenthesis, .operator_comma => Node.Index.null,
|
||||||
else => try analyzer.expression(),
|
else => try analyzer.expression(),
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
.operator_right_parenthesis,
|
.operator_right_parenthesis,
|
||||||
.operator_comma,
|
.operator_comma,
|
||||||
@ -1830,7 +1829,10 @@ const Analyzer = struct {
|
|||||||
},
|
},
|
||||||
else => |t| @panic(@tagName(t)),
|
else => |t| @panic(@tagName(t)),
|
||||||
},
|
},
|
||||||
.identifier, .discard, => b: {
|
.identifier,
|
||||||
|
.discard,
|
||||||
|
.string_literal,
|
||||||
|
=> b: {
|
||||||
analyzer.consumeToken();
|
analyzer.consumeToken();
|
||||||
|
|
||||||
switch (container_type) {
|
switch (container_type) {
|
||||||
|
@ -23,7 +23,7 @@ pub fn build(b: *std.Build) !void {
|
|||||||
const self_hosted_ci = b.option(bool, "self_hosted_ci", "This option enables the self-hosted CI behavior") orelse false;
|
const self_hosted_ci = b.option(bool, "self_hosted_ci", "This option enables the self-hosted CI behavior") orelse false;
|
||||||
const third_party_ci = b.option(bool, "third_party_ci", "This option enables the third-party CI behavior") orelse false;
|
const third_party_ci = b.option(bool, "third_party_ci", "This option enables the third-party CI behavior") orelse false;
|
||||||
const is_ci = self_hosted_ci or third_party_ci;
|
const is_ci = self_hosted_ci or third_party_ci;
|
||||||
const print_stack_trace = b.option(bool, "print_stack_trace", "This option enables printing stack traces inside the compiler") orelse is_ci or os == .macos;
|
const print_stack_trace = b.option(bool, "print_stack_trace", "This option enables printing stack traces inside the compiler") orelse is_ci;
|
||||||
const native_target = b.resolveTargetQuery(.{});
|
const native_target = b.resolveTargetQuery(.{});
|
||||||
const optimization = b.standardOptimizeOption(.{});
|
const optimization = b.standardOptimizeOption(.{});
|
||||||
const use_debug = b.option(bool, "use_debug", "This option enables the LLVM debug build in the development PC") orelse false;
|
const use_debug = b.option(bool, "use_debug", "This option enables the LLVM debug build in the development PC") orelse false;
|
||||||
|
@ -41,6 +41,77 @@ const MapFlags = switch (os) {
|
|||||||
else => #error("OS not supported"),
|
else => #error("OS not supported"),
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const AccessMode = enum(u2) {
|
||||||
|
read_only = 0,
|
||||||
|
write_only = 1,
|
||||||
|
read_write = 2,
|
||||||
|
};
|
||||||
|
|
||||||
|
const OpenFlags = switch (os) {
|
||||||
|
.macos => bitfield(u32) {
|
||||||
|
access_mode: AccessMode,
|
||||||
|
non_block: bool = false,
|
||||||
|
append: bool = false,
|
||||||
|
shared_lock: bool = false,
|
||||||
|
exclusive_lock: bool = false,
|
||||||
|
async: bool = false,
|
||||||
|
sync: bool = false,
|
||||||
|
no_follow: bool = false,
|
||||||
|
creat: bool = false,
|
||||||
|
truncate: bool = false,
|
||||||
|
exclusive: bool = false,
|
||||||
|
_: u3 = 0,
|
||||||
|
evt_only: bool = false,
|
||||||
|
_: u1 = 0,
|
||||||
|
no_ctty: bool = false,
|
||||||
|
_: u2 = 0,
|
||||||
|
directory: bool = false,
|
||||||
|
symlink: bool = false,
|
||||||
|
dsync: bool = false,
|
||||||
|
_: u1 = 0,
|
||||||
|
cloexec: bool = false,
|
||||||
|
_: u4 = 0,
|
||||||
|
alert: bool = false,
|
||||||
|
_: u1 = 0,
|
||||||
|
popup: bool = false,
|
||||||
|
},
|
||||||
|
.linux => linux.OpenFlags,
|
||||||
|
else => #error("OS not supported"),
|
||||||
|
};
|
||||||
|
|
||||||
|
const TimeSpec = struct{
|
||||||
|
seconds: s64,
|
||||||
|
nanoseconds: s64,
|
||||||
|
};
|
||||||
|
|
||||||
|
const Stat = switch (os) {
|
||||||
|
.macos => struct{
|
||||||
|
dev: s32,
|
||||||
|
mode: u16,
|
||||||
|
nlink: u16,
|
||||||
|
|
||||||
|
inode: u64,
|
||||||
|
uid: u32,
|
||||||
|
gid: u32,
|
||||||
|
rdev: s32,
|
||||||
|
|
||||||
|
a_timespec: TimeSpec,
|
||||||
|
m_timespec: TimeSpec,
|
||||||
|
c_timespec: TimeSpec,
|
||||||
|
birth_timespec: TimeSpec,
|
||||||
|
size: s64,
|
||||||
|
blocks: s64,
|
||||||
|
block_size: s32,
|
||||||
|
flags: u32,
|
||||||
|
gen: u32,
|
||||||
|
lspare: s32,
|
||||||
|
qspare: [2]s64,
|
||||||
|
},
|
||||||
|
.linux => linux.Stat,
|
||||||
|
else => #error("OS not supported"),
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
const FileDescriptor = s32;
|
const FileDescriptor = s32;
|
||||||
const ProcessId = s32;
|
const ProcessId = s32;
|
||||||
const MAP_FAILED = 0xffffffffffffffff;
|
const MAP_FAILED = 0xffffffffffffffff;
|
||||||
@ -71,7 +142,9 @@ const get_map_flags = fn(flags: std.os.MapFlags) MapFlags{
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
const write :: extern = fn cc(.c) (file_descriptor: FileDescriptor, bytes_ptr: [&]const u8, bytes_len: usize) ssize;
|
const open :: extern = fn cc(.c) (path: [&:0]const u8, flags: OpenFlags) s32;
|
||||||
|
const read :: extern = fn cc(.c) (file_descriptor: FileDescriptor, bytes_ptr: [&]const u8, byte_count: usize) ssize;
|
||||||
|
const write :: extern = fn cc(.c) (file_descriptor: FileDescriptor, bytes_ptr: [&]const u8, byte_count: usize) ssize;
|
||||||
const exit :: extern = fn cc(.c) (exit_code: s32) noreturn;
|
const exit :: extern = fn cc(.c) (exit_code: s32) noreturn;
|
||||||
const fork :: extern = fn cc(.c) () ProcessId;
|
const fork :: extern = fn cc(.c) () ProcessId;
|
||||||
const mmap :: extern = fn cc(.c) (address: ?[&]const u8, length: usize, protection_flags: ProtectionFlags, map_flags: MapFlags, file_descriptor: FileDescriptor, offset: u64) usize;
|
const mmap :: extern = fn cc(.c) (address: ?[&]const u8, length: usize, protection_flags: ProtectionFlags, map_flags: MapFlags, file_descriptor: FileDescriptor, offset: u64) usize;
|
||||||
@ -80,5 +153,6 @@ const execve :: extern = fn cc(.c) (path: [&:0]const u8, argv: [&:null]const ?[&
|
|||||||
const realpath :: extern = fn cc(.c) (path: [&:0]const u8, resolved_path: [&:0]u8) ?[&:0]u8;
|
const realpath :: extern = fn cc(.c) (path: [&:0]const u8, resolved_path: [&:0]u8) ?[&:0]u8;
|
||||||
const waitpid :: extern = fn cc(.c) (pid: ProcessId, status: &s32, flags: s32) s32;
|
const waitpid :: extern = fn cc(.c) (pid: ProcessId, status: &s32, flags: s32) s32;
|
||||||
const mprotect :: extern = fn cc(.c) (address: &any, size: usize, flags: ProtectionFlags) s32;
|
const mprotect :: extern = fn cc(.c) (address: &any, size: usize, flags: ProtectionFlags) s32;
|
||||||
|
const fstat :: extern = fn cc(.c) (file_descriptor: FileDescriptor, stat: &Stat) s32;
|
||||||
|
|
||||||
const _NSGetExecutablePath :: extern = fn cc(.c) (buffer: [&:0]u8, buffer_size: &u32) s32;
|
const _NSGetExecutablePath :: extern = fn cc(.c) (buffer: [&:0]u8, buffer_size: &u32) s32;
|
||||||
|
@ -46,17 +46,9 @@ const FileDescriptor = struct{
|
|||||||
const read = fn(file_descriptor: FileDescriptor, bytes: []u8) ReadError!usize {
|
const read = fn(file_descriptor: FileDescriptor, bytes: []u8) ReadError!usize {
|
||||||
if (bytes.length > 0) {
|
if (bytes.length > 0) {
|
||||||
switch (current) {
|
switch (current) {
|
||||||
.linux => {
|
.linux, .macos => {
|
||||||
const len: usize = #min(max_file_operation_byte_count, bytes.length);
|
const len: usize = #min(max_file_operation_byte_count, bytes.length);
|
||||||
const syscall_result = system.read(file_descriptor.handle, bytes);
|
const syscall_result = system.read(file_descriptor.handle, bytes.pointer, bytes.length);
|
||||||
const byte_count = unwrap_syscall(syscall_result) catch |err| switch (err) {
|
|
||||||
else => return ReadError.failed,
|
|
||||||
};
|
|
||||||
return byte_count;
|
|
||||||
},
|
|
||||||
.macos => {
|
|
||||||
const len: usize = #min(max_file_operation_byte_count, bytes.length);
|
|
||||||
const syscall_result = system.read(file_descriptor.handle, bytes);
|
|
||||||
const byte_count = unwrap_syscall(syscall_result) catch |err| switch (err) {
|
const byte_count = unwrap_syscall(syscall_result) catch |err| switch (err) {
|
||||||
else => return ReadError.failed,
|
else => return ReadError.failed,
|
||||||
};
|
};
|
||||||
@ -119,13 +111,8 @@ const FileDescriptor = struct{
|
|||||||
}
|
}
|
||||||
|
|
||||||
const get_size = fn (file_descriptor: FileDescriptor) GetAttributesError!u64 {
|
const get_size = fn (file_descriptor: FileDescriptor) GetAttributesError!u64 {
|
||||||
switch (current) {
|
const file_attributes = try file_descriptor.get_attributes();
|
||||||
.linux => {
|
return file_attributes.size;
|
||||||
const file_attributes = try file_descriptor.get_attributes();
|
|
||||||
return file_attributes.size;
|
|
||||||
},
|
|
||||||
else => #error("OS not supported"),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const GetAttributesError = error{
|
const GetAttributesError = error{
|
||||||
@ -134,9 +121,9 @@ const FileDescriptor = struct{
|
|||||||
|
|
||||||
const get_attributes = fn (file_descriptor: FileDescriptor) GetAttributesError!FileAttributes {
|
const get_attributes = fn (file_descriptor: FileDescriptor) GetAttributesError!FileAttributes {
|
||||||
switch (current) {
|
switch (current) {
|
||||||
.linux => {
|
.linux, .macos => {
|
||||||
var stat_buffer: linux.Stat = undefined;
|
var stat_buffer: system.Stat = undefined;
|
||||||
const raw_result = linux.fstat(file_descriptor.handle, stat_buffer.&);
|
const raw_result = system.fstat(file_descriptor.handle, stat_buffer.&);
|
||||||
const result = unwrap_syscall(raw_result) catch |err| switch (err) {
|
const result = unwrap_syscall(raw_result) catch |err| switch (err) {
|
||||||
else => return GetAttributesError.failed,
|
else => return GetAttributesError.failed,
|
||||||
};
|
};
|
||||||
@ -396,14 +383,34 @@ const AccessMode = enum(u2) {
|
|||||||
const open = fn(path: [&:0]const u8, open_flags: OpenFlags) OpenError!FileDescriptor{
|
const open = fn(path: [&:0]const u8, open_flags: OpenFlags) OpenError!FileDescriptor{
|
||||||
switch (current) {
|
switch (current) {
|
||||||
.linux => {
|
.linux => {
|
||||||
const flags = linux.OpenFlags{
|
const flags = system.OpenFlags{
|
||||||
.access_mode = switch (open_flags.access_mode) {
|
.access_mode = switch (open_flags.access_mode) {
|
||||||
.read_only => .read_only,
|
.read_only => .read_only,
|
||||||
.write_only => .write_only,
|
.write_only => .write_only,
|
||||||
.read_write => .read_write,
|
.read_write => .read_write,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
const syscall_result = linux.open(path, flags, 0);
|
const syscall_result = system.open(path, flags, 0);
|
||||||
|
const result = unwrap_syscall(syscall_result) catch |err| switch (err) {
|
||||||
|
else => unreachable,
|
||||||
|
};
|
||||||
|
|
||||||
|
const r: u32 = #cast(result);
|
||||||
|
|
||||||
|
const file_descriptor = FileDescriptor{
|
||||||
|
.handle = #cast(r),
|
||||||
|
};
|
||||||
|
return file_descriptor;
|
||||||
|
},
|
||||||
|
.macos => {
|
||||||
|
const flags = system.OpenFlags{
|
||||||
|
.access_mode = switch (open_flags.access_mode) {
|
||||||
|
.read_only => .read_only,
|
||||||
|
.write_only => .write_only,
|
||||||
|
.read_write => .read_write,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
const syscall_result = system.open(path, flags);
|
||||||
const result = unwrap_syscall(syscall_result) catch |err| switch (err) {
|
const result = unwrap_syscall(syscall_result) catch |err| switch (err) {
|
||||||
else => unreachable,
|
else => unreachable,
|
||||||
};
|
};
|
||||||
|
@ -919,8 +919,8 @@ const openat = fn(directory_file_descriptor: FileDescriptor, path: [&:0]const u8
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
const read = fn(file_descriptor: FileDescriptor, bytes: []u8) usize {
|
const read = fn(file_descriptor: FileDescriptor, byte_pointer: [&]u8, byte_count: usize) usize {
|
||||||
const result = #syscall(#cast(Syscall.read), #cast(file_descriptor), #cast(bytes.pointer), bytes.length);
|
const result = #syscall(#cast(Syscall.read), #cast(file_descriptor), #cast(byte_pointer), byte_count);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
44
src/main.nat
44
src/main.nat
@ -19,6 +19,45 @@ const Token = struct {
|
|||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const FixedKeyword = enum{
|
||||||
|
"comptime",
|
||||||
|
"const",
|
||||||
|
"var",
|
||||||
|
"void",
|
||||||
|
"noreturn",
|
||||||
|
"while",
|
||||||
|
"bool",
|
||||||
|
"true",
|
||||||
|
"false",
|
||||||
|
"fn",
|
||||||
|
"unreachable",
|
||||||
|
"return",
|
||||||
|
"ssize",
|
||||||
|
"usize",
|
||||||
|
""switch",
|
||||||
|
"if",
|
||||||
|
"else",
|
||||||
|
"struct",
|
||||||
|
"enum",
|
||||||
|
"null",
|
||||||
|
"align",
|
||||||
|
"for",
|
||||||
|
"undefined",
|
||||||
|
"break",
|
||||||
|
"test",
|
||||||
|
"catch",
|
||||||
|
"try",
|
||||||
|
"orelse",
|
||||||
|
"error",
|
||||||
|
"and",
|
||||||
|
"or",
|
||||||
|
"bitfield",
|
||||||
|
"Self",
|
||||||
|
"any",
|
||||||
|
"type",
|
||||||
|
"continue",
|
||||||
|
};
|
||||||
|
|
||||||
const lex = fn (arena: &Arena, bytes: []const u8) *!void {
|
const lex = fn (arena: &Arena, bytes: []const u8) *!void {
|
||||||
if (bytes.length >= 0xffffffff) {
|
if (bytes.length >= 0xffffffff) {
|
||||||
unreachable;
|
unreachable;
|
||||||
@ -72,10 +111,11 @@ const lex = fn (arena: &Arena, bytes: []const u8) *!void {
|
|||||||
's' => .keyword_signed_integer,
|
's' => .keyword_signed_integer,
|
||||||
else => unreachable,
|
else => unreachable,
|
||||||
};
|
};
|
||||||
} else {
|
|
||||||
//unreachable;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const string_length = index - start_index;
|
||||||
|
const string = bytes[start_index..][0..string_length];
|
||||||
},
|
},
|
||||||
else => index += 1,
|
else => index += 1,
|
||||||
}
|
}
|
||||||
|
18
test/standalone/comptime_for/main.nat
Normal file
18
test/standalone/comptime_for/main.nat
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
const std = #import("std");
|
||||||
|
const print = std.print;
|
||||||
|
|
||||||
|
const Enum = enum{
|
||||||
|
first_name,
|
||||||
|
second_name,
|
||||||
|
third_name,
|
||||||
|
};
|
||||||
|
|
||||||
|
const main = fn () *!void {
|
||||||
|
print("Enum values:\n");
|
||||||
|
|
||||||
|
for ($#fields(Enum)) |e| {
|
||||||
|
const name: []const u8 = #name(e);
|
||||||
|
print(name);
|
||||||
|
print("\n");
|
||||||
|
}
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user