diff options
| author | Bruce Hill <bruce@bruce-hill.com> | 2024-03-24 15:06:59 -0400 |
|---|---|---|
| committer | Bruce Hill <bruce@bruce-hill.com> | 2024-03-24 15:06:59 -0400 |
| commit | 5157988efa388f956d3ea8204e496baf6db11b52 (patch) | |
| tree | b1cc89f2244d21de4811a3467b4bc15f795b7019 /compile.c | |
| parent | a29d2ed6d1735d4f12dd250900785db4271edeca (diff) | |
Implement 'extern' functionality
Diffstat (limited to 'compile.c')
| -rw-r--r-- | compile.c | 20 |
1 files changed, 19 insertions, 1 deletions
@@ -58,7 +58,6 @@ static bool promote(env_t *env, CORD *code, type_t *actual, type_t *needed) return false; } - CORD compile_declaration(env_t *env, type_t *t, const char *name) { if (t->tag == FunctionType) { @@ -735,6 +734,25 @@ CORD compile_statement(env_t *env, ast_t *ast) return compile_statement(env, loop); } } + case Extern: { + auto ext = Match(ast, Extern); + type_t *t = parse_type_ast(env, ext->type); + CORD decl; + if (t->tag == ClosureType) { + t = Match(t, ClosureType)->fn; + auto fn = Match(t, FunctionType); + decl = CORD_all(compile_type(env, fn->ret), " ", ext->name, "("); + for (arg_t *arg = fn->args; arg; arg = arg->next) { + decl = CORD_all(decl, compile_type(env, arg->type)); + if (arg->next) decl = CORD_cat(decl, ", "); + } + decl = CORD_cat(decl, ")"); + } else { + decl = compile_declaration(env, t, ext->name); + } + env->code->fndefs = CORD_all(env->code->fndefs, "extern ", decl, ";\n"); + return CORD_EMPTY; + } case InlineCCode: return Match(ast, InlineCCode)->code; default: return CORD_asprintf("(void)%r;", compile(env, ast)); |
