@@ -11,9 +11,11 @@ const warn = std.debug.warn;
11
11
const Token = std .zig .Token ;
12
12
const ArrayList = std .ArrayList ;
13
13
const errmsg = @import ("errmsg.zig" );
14
+ const ast = std .zig .ast ;
15
+ const event = std .event ;
14
16
15
17
pub const Module = struct {
16
- allocator : * mem.Allocator ,
18
+ loop : * event.Loop ,
17
19
name : Buffer ,
18
20
root_src_path : ? []const u8 ,
19
21
module : llvm.ModuleRef ,
@@ -76,6 +78,51 @@ pub const Module = struct {
76
78
77
79
kind : Kind ,
78
80
81
+ link_out_file : ? []const u8 ,
82
+ events : * event .Channel (Event ),
83
+
84
+ // TODO handle some of these earlier and report them in a way other than error codes
85
+ pub const BuildError = error {
86
+ OutOfMemory ,
87
+ EndOfStream ,
88
+ BadFd ,
89
+ Io ,
90
+ IsDir ,
91
+ Unexpected ,
92
+ SystemResources ,
93
+ SharingViolation ,
94
+ PathAlreadyExists ,
95
+ FileNotFound ,
96
+ AccessDenied ,
97
+ PipeBusy ,
98
+ FileTooBig ,
99
+ SymLinkLoop ,
100
+ ProcessFdQuotaExceeded ,
101
+ NameTooLong ,
102
+ SystemFdQuotaExceeded ,
103
+ NoDevice ,
104
+ PathNotFound ,
105
+ NoSpaceLeft ,
106
+ NotDir ,
107
+ FileSystem ,
108
+ OperationAborted ,
109
+ IoPending ,
110
+ BrokenPipe ,
111
+ WouldBlock ,
112
+ FileClosed ,
113
+ DestinationAddressRequired ,
114
+ DiskQuota ,
115
+ InputOutput ,
116
+ NoStdHandles ,
117
+ Overflow ,
118
+ };
119
+
120
+ pub const Event = union (enum ) {
121
+ Ok ,
122
+ Fail : []errmsg.Msg ,
123
+ Error : BuildError ,
124
+ };
125
+
79
126
pub const DarwinVersionMin = union (enum ) {
80
127
None ,
81
128
MacOS : []const u8 ,
@@ -104,7 +151,7 @@ pub const Module = struct {
104
151
};
105
152
106
153
pub fn create (
107
- allocator : * mem.Allocator ,
154
+ loop : * event.Loop ,
108
155
name : []const u8 ,
109
156
root_src_path : ? []const u8 ,
110
157
target : * const Target ,
@@ -113,7 +160,7 @@ pub const Module = struct {
113
160
zig_lib_dir : []const u8 ,
114
161
cache_dir : []const u8 ,
115
162
) ! * Module {
116
- var name_buffer = try Buffer .init (allocator , name );
163
+ var name_buffer = try Buffer .init (loop . allocator , name );
117
164
errdefer name_buffer .deinit ();
118
165
119
166
const context = c .LLVMContextCreate () orelse return error .OutOfMemory ;
@@ -125,8 +172,12 @@ pub const Module = struct {
125
172
const builder = c .LLVMCreateBuilderInContext (context ) orelse return error .OutOfMemory ;
126
173
errdefer c .LLVMDisposeBuilder (builder );
127
174
128
- const module_ptr = try allocator .create (Module {
129
- .allocator = allocator ,
175
+ const events = try event .Channel (Event ).create (loop , 0 );
176
+ errdefer events .destroy ();
177
+
178
+ return loop .allocator .create (Module {
179
+ .loop = loop ,
180
+ .events = events ,
130
181
.name = name_buffer ,
131
182
.root_src_path = root_src_path ,
132
183
.module = module ,
@@ -171,76 +222,87 @@ pub const Module = struct {
171
222
.link_objects = [][]const u8 {},
172
223
.windows_subsystem_windows = false ,
173
224
.windows_subsystem_console = false ,
174
- .link_libs_list = ArrayList (* LinkLib ).init (allocator ),
225
+ .link_libs_list = ArrayList (* LinkLib ).init (loop . allocator ),
175
226
.libc_link_lib = null ,
176
227
.err_color = errmsg .Color .Auto ,
177
228
.darwin_frameworks = [][]const u8 {},
178
229
.darwin_version_min = DarwinVersionMin .None ,
179
230
.test_filters = [][]const u8 {},
180
231
.test_name_prefix = null ,
181
232
.emit_file_type = Emit .Binary ,
233
+ .link_out_file = null ,
182
234
});
183
- errdefer allocator .destroy (module_ptr );
184
- return module_ptr ;
185
235
}
186
236
187
237
fn dump (self : * Module ) void {
188
238
c .LLVMDumpModule (self .module );
189
239
}
190
240
191
241
pub fn destroy (self : * Module ) void {
242
+ self .events .destroy ();
192
243
c .LLVMDisposeBuilder (self .builder );
193
244
c .LLVMDisposeModule (self .module );
194
245
c .LLVMContextDispose (self .context );
195
246
self .name .deinit ();
196
247
197
- self .allocator .destroy (self );
248
+ self .a () .destroy (self );
198
249
}
199
250
200
251
pub fn build (self : * Module ) ! void {
201
252
if (self .llvm_argv .len != 0 ) {
202
- var c_compatible_args = try std .cstr .NullTerminated2DArray .fromSlices (self .allocator , [][]const []const u8 {
253
+ var c_compatible_args = try std .cstr .NullTerminated2DArray .fromSlices (self .a () , [][]const []const u8 {
203
254
[][]const u8 {"zig (LLVM option parsing)" },
204
255
self .llvm_argv ,
205
256
});
206
257
defer c_compatible_args .deinit ();
258
+ // TODO this sets global state
207
259
c .ZigLLVMParseCommandLineOptions (self .llvm_argv .len + 1 , c_compatible_args .ptr );
208
260
}
209
261
262
+ _ = try async < self .a ()> self .buildAsync ();
263
+ }
264
+
265
+ async fn buildAsync (self : * Module ) void {
266
+ while (true ) {
267
+ // TODO directly awaiting async should guarantee memory allocation elision
268
+ // TODO also async before suspending should guarantee memory allocation elision
269
+ (await (async self .addRootSrc () catch unreachable )) catch | err | {
270
+ await (async self .events .put (Event { .Error = err }) catch unreachable );
271
+ return ;
272
+ };
273
+ await (async self .events .put (Event .Ok ) catch unreachable );
274
+ }
275
+ }
276
+
277
+ async fn addRootSrc (self : * Module ) ! void {
210
278
const root_src_path = self .root_src_path orelse @panic ("TODO handle null root src path" );
211
- const root_src_real_path = os .path .real (self .allocator , root_src_path ) catch | err | {
279
+ const root_src_real_path = os .path .real (self .a () , root_src_path ) catch | err | {
212
280
try printError ("unable to get real path '{}': {}" , root_src_path , err );
213
281
return err ;
214
282
};
215
- errdefer self .allocator .free (root_src_real_path );
283
+ errdefer self .a () .free (root_src_real_path );
216
284
217
- const source_code = io .readFileAlloc (self .allocator , root_src_real_path ) catch | err | {
285
+ const source_code = io .readFileAlloc (self .a () , root_src_real_path ) catch | err | {
218
286
try printError ("unable to open '{}': {}" , root_src_real_path , err );
219
287
return err ;
220
288
};
221
- errdefer self .allocator .free (source_code );
222
-
223
- warn ("====input:====\n " );
224
-
225
- warn ("{}" , source_code );
289
+ errdefer self .a ().free (source_code );
226
290
227
- warn ("====parse:====\n " );
228
-
229
- var tree = try std .zig .parse (self .allocator , source_code );
291
+ var tree = try std .zig .parse (self .a (), source_code );
230
292
defer tree .deinit ();
231
293
232
- var stderr_file = try std . io . getStdErr ();
233
- var stderr_file_out_stream = std . io . FileOutStream . init ( & stderr_file );
234
- const out_stream = & stderr_file_out_stream . stream ;
235
-
236
- warn ( "====fmt:==== \n " );
237
- _ = try std . zig . render ( self . allocator , out_stream , & tree );
238
-
239
- warn ( "====ir:==== \n " );
240
- warn ("TODO\n\n " );
241
-
242
- warn ( "====llvm ir:==== \n " );
243
- self . dump ();
294
+ // var it = tree.root_node.decls.iterator ();
295
+ //while (it.next()) |decl_ptr| {
296
+ // const decl = decl_ptr.* ;
297
+ // switch (decl.id) {
298
+ // ast.Node.Comptime => @panic("TODO"),
299
+ // ast.Node.VarDecl => @panic("TODO"),
300
+ // ast.Node.UseDecl => @panic("TODO"),
301
+ // ast.Node.FnDef => @panic("TODO"),
302
+ // ast.Node.TestDecl => @panic ("TODO"),
303
+ // else => unreachable,
304
+ // }
305
+ //}
244
306
}
245
307
246
308
pub fn link (self : * Module , out_file : ? []const u8 ) ! void {
@@ -263,18 +325,22 @@ pub const Module = struct {
263
325
}
264
326
}
265
327
266
- const link_lib = try self .allocator .create (LinkLib {
328
+ const link_lib = try self .a () .create (LinkLib {
267
329
.name = name ,
268
330
.path = null ,
269
331
.provided_explicitly = provided_explicitly ,
270
- .symbols = ArrayList ([]u8 ).init (self .allocator ),
332
+ .symbols = ArrayList ([]u8 ).init (self .a () ),
271
333
});
272
334
try self .link_libs_list .append (link_lib );
273
335
if (is_libc ) {
274
336
self .libc_link_lib = link_lib ;
275
337
}
276
338
return link_lib ;
277
339
}
340
+
341
+ fn a (self : Module ) * mem.Allocator {
342
+ return self .loop .allocator ;
343
+ }
278
344
};
279
345
280
346
fn printError (comptime format : []const u8 , args : ... ) ! void {
0 commit comments