Skip to content

Commit ed67ea4

Browse files
committed
Compiler: force zero initialization of local variables
* make all local variables zero-initialized except if tagged as `@(noinit)` * update tests
1 parent f274094 commit ed67ea4

33 files changed

+99
-68
lines changed

ast/ast_evaluator.c2

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -284,17 +284,17 @@ fn Value Evaluator.eval_call(Evaluator* caller, const CallExpr* c) {
284284

285285
// Create a new stack frame and link it to the caller's
286286
// TODO: handle Stack frames as separate allocated objects
287-
Evaluator eval;
288-
289-
if (num_args > elemsof(eval.args)) {
290-
return Value.error("too many arguments in pure function evaluation");
291-
}
287+
Evaluator eval /*@(noinit)*/;
292288
eval.prev = caller;
293289
eval.fd = fd;
294290
eval.num_args = num_args;
295291
eval.depth = caller.depth + 1;
296292
eval.complexity = caller.complexity + 1;
297293

294+
if (num_args > elemsof(eval.args)) {
295+
return Value.error("too many arguments in pure function evaluation");
296+
}
297+
298298
//VarDecl** params = fd.getParams();
299299

300300
for (u32 i = 0; i < num_args; i++) {

ast/value.c2

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -804,7 +804,7 @@ fn f64 fabs(f64 d) {
804804
// string and trying to avoid using exponential notation
805805
// TODO: should be in the C2 library as a type function f64.str()
806806
public fn char *ftoa(char *dest, usize size, f64 d) {
807-
char[32] buf;
807+
char[32] buf /*@(noinit)*/;
808808
usize pos = 0;
809809

810810
if (size < 2) {

ast/var_decl.c2

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,7 @@ type VarDeclBits struct {
5757
u32 addr_used : 1;
5858
AutoAttr auto_attr : 2; // for parameters only
5959
FormatAttr format_attr : 2; // for parameters only
60+
u32 attr_noinit : 1;
6061
}
6162

6263
public type BitFieldLayout struct {
@@ -303,6 +304,14 @@ public fn bool VarDecl.hasInitCall(const VarDecl* d) {
303304
return d.base.varDeclBits.has_init_call;
304305
}
305306

307+
public fn void VarDecl.setAttrNoInit(VarDecl* d) {
308+
d.base.varDeclBits.attr_noinit = 1;
309+
}
310+
311+
public fn bool VarDecl.hasAttrNoInit(const VarDecl* d) {
312+
return d.base.varDeclBits.attr_noinit;
313+
}
314+
306315
public fn void VarDecl.setAttrWeak(VarDecl* d) {
307316
d.base.varDeclBits.attr_weak = 1;
308317
}

ast_utils/attr.c2

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ public type AttrKind enum u8 {
4444
AutoFunc, // Var, function param only
4545
Embed, // Var, globals only
4646
Deprecated, // Func
47+
NoInit, // Var
4748
}
4849

4950
const char*[AttrKind] attrKind_names = {
@@ -71,6 +72,7 @@ const char*[AttrKind] attrKind_names = {
7172
"auto_func",
7273
"embed",
7374
"deprecated",
75+
"noinit",
7476
}
7577

7678
public type AttrValueKind enum u8 {
@@ -148,6 +150,7 @@ const AttrReq[AttrKind] Required_arg = {
148150
[AutoFunc] = NoArg,
149151
[Embed] = String,
150152
[Deprecated] = String,
153+
[NoInit] = NoArg,
151154
}
152155

153156
public type AttrReq enum u8 {

ast_utils/string_buffer.c2

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -169,7 +169,7 @@ public fn void Buf.stripTrailingSpaces(Buf* buf) {
169169
}
170170

171171
public fn void Buf.print(Buf* buf, const char* format @(printf_format), ...) {
172-
char[4096] tmp;
172+
char[4096] tmp /*@(noinit)*/;
173173
// NOTE: no growing
174174
va_list args;
175175
va_start(args, format);
@@ -180,7 +180,7 @@ public fn void Buf.print(Buf* buf, const char* format @(printf_format), ...) {
180180
}
181181

182182
public fn void Buf.vprintf(Buf* buf, const char* format, va_list args) {
183-
char[4096] tmp;
183+
char[4096] tmp /*@(noinit)*/;
184184
// NOTE: no growing
185185
i32 len = vsnprintf(tmp, elemsof(tmp), format, args);
186186
assert(len < elemsof(tmp));

common/ast_builder.c2

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -511,6 +511,9 @@ fn void Builder.actOnVarAttr(Builder* b, Decl* d, const Attr* a) {
511511
case Embed:
512512
b.storeAttr(d, a);
513513
break;
514+
case NoInit:
515+
vd.setAttrNoInit();
516+
break;
514517
default:
515518
b.diags.error(a.loc, "attribute '%s' is not applicable to variables",
516519
a.kind2name());

common/file/file_utils.c2

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -116,7 +116,7 @@ public fn const char* make_path3(char *buf, usize size, const char* dir, const c
116116
// returns 0 on success, errno on failure
117117
// create a directory path, OK if exists already
118118
public fn i32 create_path(const char* path) {
119-
char[file_utils.Max_path] tmp;
119+
char[file_utils.Max_path] tmp /*@(noinit)*/;
120120
char *p = tmp;
121121
if (!*path) return 0;
122122
*p++ = *path++;

generator/c/c_generator.c2

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1295,8 +1295,7 @@ public fn void generate(string_pool.Pool* astPool,
12951295
return;
12961296
}
12971297

1298-
Generator gen;
1299-
gen.init(astPool, target, kind, output_dir, dir, diags, sm, build_info, mainFunc);
1298+
Generator gen.init(astPool, target, kind, output_dir, dir, diags, sm, build_info, mainFunc);
13001299
gen.auxPool = auxPool;
13011300
gen.enable_asserts = enable_asserts;
13021301
gen.fast_build = fast_build;

generator/c/c_generator_special.c2

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,7 @@ fn void Generator.createMakefile(Generator* gen,
6060
out.print("CC=%s\n", cc);
6161

6262
out.add("CFLAGS=-Wall -Wextra -Wno-unused -Wno-switch\n");
63-
out.add("CFLAGS+=-Wno-unused-parameter -Wno-missing-field-initializers -Wno-format-zero-length\n");
63+
out.add("CFLAGS+=-Wno-unused-parameter -Wno-missing-field-initializers -Wno-missing-braces -Wno-format-zero-length\n");
6464
out.add("CFLAGS+=-pipe -std=c99 -funsigned-char\n");
6565
if (gen.fast_build)
6666
out.add("CFLAGS+=-O0 -g\n");

generator/c/c_generator_stmt.c2

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,10 @@ fn void Generator.emitVarDecl(Generator* gen, VarDecl* vd, string_buffer.Buf* ou
4040
out.add(" = ");
4141
}
4242
gen.emitExpr(out, ie);
43+
} else {
44+
if (!vd.hasAttrNoInit()) {
45+
out.add(" = { 0 }");
46+
}
4347
}
4448
}
4549

0 commit comments

Comments
 (0)