summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--cgen.c40
-rw-r--r--copy.c16
-rw-r--r--err.c6
-rw-r--r--eval.c8
-rw-r--r--parse.c43
-rw-r--r--sdecls_cgen.c4
-rw-r--r--test.toc15
-rw-r--r--types.c22
-rw-r--r--types.h10
9 files changed, 84 insertions, 80 deletions
diff --git a/cgen.c b/cgen.c
index 9a45984..ba14ebb 100644
--- a/cgen.c
+++ b/cgen.c
@@ -75,26 +75,28 @@ static void cgen_defs_decl(CGenerator *g, Declaration *d);
f(g, arg); \
break; \
case EXPR_BLOCK: \
- block_f(g, &e->block); \
+ block_f(g, e->block); \
break; \
case EXPR_NMS: { \
Namespace *prev = g->nms; \
- g->nms = &e->nms; \
- block_f(g, &e->nms.body); \
+ g->nms = e->nms; \
+ block_f(g, &e->nms->body); \
g->nms = prev; \
} break; \
- case EXPR_IF: \
- if (e->if_.cond) \
- f(g, e->if_.cond); \
- block_f(g, &e->if_.body); \
- if (e->if_.next_elif) \
- f(g, e->if_.next_elif); \
- break; \
- case EXPR_WHILE: \
- if (e->while_.cond) \
- f(g, e->while_.cond); \
- block_f(g, &e->while_.body); \
- break; \
+ case EXPR_IF: { \
+ IfExpr *i = e->if_; \
+ if (i->cond) \
+ f(g, i->cond); \
+ block_f(g, &i->body); \
+ if (i->next_elif) \
+ f(g, i->next_elif); \
+ } break; \
+ case EXPR_WHILE: { \
+ WhileExpr *w = e->while_; \
+ if (w->cond) \
+ f(g, w->cond); \
+ block_f(g, &w->body); \
+ } break; \
case EXPR_FOR: { \
ForExpr *fo = e->for_; \
if (fo->flags & FOR_IS_RANGE) { \
@@ -787,7 +789,7 @@ static void cgen_expr_pre(CGenerator *g, Expression *e) {
switch (e->kind) {
case EXPR_IF: {
- IfExpr *curr = &e->if_;
+ IfExpr *curr = e->if_;
e->cgen.id = id;
while (1) {
if (curr->cond) {
@@ -798,12 +800,12 @@ static void cgen_expr_pre(CGenerator *g, Expression *e) {
cgen_block(g, &curr->body, ret_name, 0);
if (curr->next_elif) {
cgen_write(g, " else ");
- curr = &curr->next_elif->if_;
+ curr = curr->next_elif->if_;
} else break;
}
} break;
case EXPR_WHILE: {
- WhileExpr *w = &e->while_;
+ WhileExpr *w = e->while_;
e->cgen.id = id;
cgen_write(g, "while (");
if (w->cond) {
@@ -989,7 +991,7 @@ static void cgen_expr_pre(CGenerator *g, Expression *e) {
} break;
case EXPR_BLOCK:
e->cgen.id = id;
- cgen_block(g, &e->block, ret_name, 0);
+ cgen_block(g, e->block, ret_name, 0);
break;
case EXPR_CALL: {
cgen_expr_pre(g, e->call.fn);
diff --git a/copy.c b/copy.c
index 0699474..28115d2 100644
--- a/copy.c
+++ b/copy.c
@@ -228,8 +228,9 @@ static void copy_expr(Copier *c, Expression *out, Expression *in) {
out->binary.rhs = copy_expr_(c, in->binary.rhs);
break;
case EXPR_IF: {
- IfExpr *iin = &in->if_;
- IfExpr *iout = &out->if_;
+ IfExpr *iin = in->if_;
+ IfExpr *iout = out->if_ = allocr_malloc(a, sizeof *iout);
+ *iout = *iin;
if (iin->cond)
iout->cond = copy_expr_(c, iin->cond);
if (iin->next_elif)
@@ -237,8 +238,9 @@ static void copy_expr(Copier *c, Expression *out, Expression *in) {
copy_block(c, &iout->body, &iin->body, 0);
} break;
case EXPR_WHILE: {
- WhileExpr *win = &in->while_;
- WhileExpr *wout = &out->while_;
+ WhileExpr *win = in->while_;
+ WhileExpr *wout = out->while_ = allocr_malloc(a, sizeof *wout);
+ *wout = *win;
if (win->cond)
wout->cond = copy_expr_(c, win->cond);
copy_block(c, &wout->body, &win->body, 0);
@@ -308,7 +310,7 @@ static void copy_expr(Copier *c, Expression *out, Expression *in) {
}
} break;
case EXPR_BLOCK:
- copy_block(c, &out->block, &in->block, 0);
+ copy_block(c, out->block = allocr_malloc(a, sizeof *out->block), in->block, 0);
break;
case EXPR_TUPLE: {
size_t nexprs = arr_len(in->tuple);
@@ -339,7 +341,9 @@ static void copy_expr(Copier *c, Expression *out, Expression *in) {
copy_val(a, &out->val, &in->val, &in->type);
break;
case EXPR_NMS:
- copy_block(c, &out->nms.body, &in->nms.body, 0);
+ out->nms = allocr_malloc(a, sizeof *out->nms);
+ *out->nms = *in->nms;
+ copy_block(c, &out->nms->body, &in->nms->body, 0);
break;
}
}
diff --git a/err.c b/err.c
index 4c81c27..3a74595 100644
--- a/err.c
+++ b/err.c
@@ -271,7 +271,7 @@ static void *err_malloc(size_t size) {
void *ret = malloc(size);
if (!ret) {
fprintf(stderr, "Error: Out of memory.\n");
- abort();
+ exit(EXIT_FAILURE);
}
#ifdef MALLOC_FILL
@@ -285,7 +285,7 @@ static void *err_calloc(size_t n, size_t size) {
void *ret = calloc(n, size);
if (!ret) {
fprintf(stderr, "Error: Out of memory.\n");
- abort();
+ exit(EXIT_FAILURE);
}
return ret;
}
@@ -298,7 +298,7 @@ static void *err_realloc(void *data, size_t new_size) {
void *ret = realloc(data, new_size);
if (!ret) {
fprintf(stderr, "Error: Out of memory.\n");
- abort();
+ exit(EXIT_FAILURE);
}
return ret;
}
diff --git a/eval.c b/eval.c
index 0b73272..08db84b 100644
--- a/eval.c
+++ b/eval.c
@@ -1187,7 +1187,7 @@ static Status eval_expr(Evaluator *ev, Expression *e, Value *v) {
}
break;
case EXPR_IF: {
- IfExpr *i = &e->if_;
+ IfExpr *i = e->if_;
if (i->cond) {
Value cond;
if (!eval_expr(ev, i->cond, &cond)) return false;
@@ -1202,7 +1202,7 @@ static Status eval_expr(Evaluator *ev, Expression *e, Value *v) {
} break;
case EXPR_WHILE: {
Value cond;
- WhileExpr *w = &e->while_;
+ WhileExpr *w = e->while_;
while (1) {
if (w->cond) {
if (!eval_expr(ev, w->cond, &cond)) return false;
@@ -1322,7 +1322,7 @@ static Status eval_expr(Evaluator *ev, Expression *e, Value *v) {
free(for_valp);
} break;
case EXPR_BLOCK:
- if (!eval_block(ev, &e->block, v)) return false;
+ if (!eval_block(ev, e->block, v)) return false;
break;
case EXPR_LITERAL_BOOL:
v->boolv = e->booll;
@@ -1529,7 +1529,7 @@ static Status eval_expr(Evaluator *ev, Expression *e, Value *v) {
v->type = &e->typeval;
break;
case EXPR_NMS:
- v->nms = &e->nms;
+ v->nms = e->nms;
break;
case EXPR_VAL:
*v = e->val;
diff --git a/parse.c b/parse.c
index bdd7608..745b965 100644
--- a/parse.c
+++ b/parse.c
@@ -1312,7 +1312,7 @@ static Status parse_expr(Parser *p, Expression *e, Token *end) {
goto success;
}
case KW_NMS: {
- Namespace *n = &e->nms;
+ Namespace *n = e->nms = parser_malloc(p, sizeof *n);
e->kind = EXPR_NMS;
++t->token;
if (!parse_block(p, &n->body, 0))
@@ -1320,7 +1320,7 @@ static Status parse_expr(Parser *p, Expression *e, Token *end) {
goto success;
}
case KW_IF: {
- IfExpr *i = &e->if_;
+ IfExpr *i = e->if_ = parser_malloc(p, sizeof *i);
e->kind = EXPR_IF;
++t->token;
Token *cond_end = expr_find_end(p, EXPR_CAN_END_WITH_LBRACE);
@@ -1351,7 +1351,7 @@ static Status parse_expr(Parser *p, Expression *e, Token *end) {
next->where = parser_mk_loc(p);
next->where.start = t->token;
curr->next_elif = next;
- IfExpr *nexti = &next->if_;
+ IfExpr *nexti = next->if_ = parser_malloc(p, sizeof *nexti);
if (is_else) {
++t->token;
nexti->cond = NULL;
@@ -1379,7 +1379,7 @@ static Status parse_expr(Parser *p, Expression *e, Token *end) {
}
case KW_WHILE: {
e->kind = EXPR_WHILE;
- WhileExpr *w = &e->while_;
+ WhileExpr *w = e->while_ = parser_malloc(p, sizeof *w);
++t->token;
if (token_is_kw(t->token, KW_LBRACE)) {
/* infinite loop */
@@ -2122,7 +2122,7 @@ static Status parse_expr(Parser *p, Expression *e, Token *end) {
if (token_is_kw(t->token, KW_LBRACE)) {
/* it's a block */
e->kind = EXPR_BLOCK;
- if (!parse_block(p, &e->block, 0)) return false;
+ if (!parse_block(p, e->block = parser_malloc(p, sizeof *e->block), 0)) return false;
if (t->token != end) {
tokr_err(t, "Expression continues after end of block."); /* TODO: improve this err message */
return false;
@@ -2418,9 +2418,10 @@ static Status parse_stmt(Parser *p, Statement *s, bool *was_a_statement) {
Expression *e = &d->expr;
e->kind = EXPR_NMS;
+ e->nms = parser_calloc(p, 1, sizeof *e->nms);
e->where = s->where;
- e->nms.associated_ident = ident;
- Block *body = &e->nms.body;
+ e->nms->associated_ident = ident;
+ Block *body = &e->nms->body;
body->flags |= BLOCK_IS_NMS;
body->where = s->where;
idents_create(&body->idents, p->allocr, body);
@@ -2639,22 +2640,24 @@ static void fprint_expr(FILE *out, Expression *e) {
fprintf(out, "new ");
fprint_type(out, &e->new.type);
break;
- case EXPR_IF:
- if (e->if_.cond) {
+ case EXPR_IF: {
+ IfExpr *i = e->if_;
+ if (i->cond) {
fprintf(out, "(else)? if ");
- fprint_expr(out, e->if_.cond);
+ fprint_expr(out, i->cond);
} else {
fprintf(out, "else");
}
- fprint_block(out, &e->if_.body);
- if (e->if_.next_elif)
- fprint_expr(out, e->if_.next_elif);
- break;
- case EXPR_WHILE:
+ fprint_block(out, &i->body);
+ if (i->next_elif)
+ fprint_expr(out, i->next_elif);
+ } break;
+ case EXPR_WHILE: {
+ WhileExpr *w = e->while_;
fprintf(out, "while ");
- if (e->while_.cond) fprint_expr(out, e->while_.cond);
- fprint_block(out, &e->while_.body);
- break;
+ if (w->cond) fprint_expr(out, w->cond);
+ fprint_block(out, &w->body);
+ } break;
case EXPR_FOR: {
ForExpr *fo = e->for_;
fprintf(out, "for ");
@@ -2701,7 +2704,7 @@ static void fprint_expr(FILE *out, Expression *e) {
}
break;
case EXPR_BLOCK:
- fprint_block(out, &e->block);
+ fprint_block(out, e->block);
break;
case EXPR_TUPLE:
fprintf(out, "(");
@@ -2741,7 +2744,7 @@ static void fprint_expr(FILE *out, Expression *e) {
fprint_val(out, e->val, &e->type);
break;
case EXPR_NMS:
- fprint_nms(out, &e->nms);
+ fprint_nms(out, e->nms);
break;
}
if (found_type) {
diff --git a/sdecls_cgen.c b/sdecls_cgen.c
index 52795f7..4ad038f 100644
--- a/sdecls_cgen.c
+++ b/sdecls_cgen.c
@@ -78,7 +78,7 @@ static void cgen_sdecls_expr(CGenerator *g, Expression *e) {
cgen_sdecls_type(g, &e->typeval);
break;
case EXPR_NMS: {
- char *prefix_part = cgen_nms_prefix_part(g, &e->nms);
+ char *prefix_part = cgen_nms_prefix_part(g, e->nms);
size_t prefix_part_len = strlen(prefix_part);
char const *prev_prefix = g->nms_prefixes ? *(char const **)arr_last(g->nms_prefixes)
: "";
@@ -89,7 +89,7 @@ static void cgen_sdecls_expr(CGenerator *g, Expression *e) {
free(prefix_part);
*(char const **)arr_add(&g->nms_prefixes) = new_prefix;
new_prefix[prev_prefix_len + prefix_part_len] = 0;
- e->nms.c.prefix = new_prefix;
+ e->nms->c.prefix = new_prefix;
} break;
default: break;
}
diff --git a/test.toc b/test.toc
index 43ed69b..d442d91 100644
--- a/test.toc
+++ b/test.toc
@@ -1,15 +1,10 @@
#include "std/io.toc", io;
-Foo ::= struct(n::=12) {
- x ::= (n as float)*2.3;
-};
main ::= fn() {
- f : Foo();
- io.puti(f.n);
- io.puti(f.x as int);
- g : Foo(3);
- io.puti(g.n);
- io.puti(g.x as int);
+ if 3 > 5 {
+
+ } elif 45 > 32 {
+ } else {
+ }
};
-main(); \ No newline at end of file
diff --git a/types.c b/types.c
index c518768..2f2a8e0 100644
--- a/types.c
+++ b/types.c
@@ -561,7 +561,7 @@ static Status type_of_ident(Typer *tr, Location where, Identifier *ident, Type *
print_block_location(tr->block);
printf("But the identifier's scope is:\n");
print_block_location(i->idents->scope);
- abort();
+ abort();
}
#else
assert(i->idents->scope == tr->block);
@@ -1594,7 +1594,7 @@ static Status types_expr(Typer *tr, Expression *e) {
}
break;
case EXPR_IF: {
- IfExpr *i = &e->if_;
+ IfExpr *i = e->if_;
IfExpr *curr = i;
Type *curr_type = t;
bool has_else = false;
@@ -1620,7 +1620,7 @@ static Status types_expr(Typer *tr, Expression *e) {
has_else = true;
}
if (curr->next_elif) {
- IfExpr *nexti = &curr->next_elif->if_;
+ IfExpr *nexti = curr->next_elif->if_;
Type *next_type = &curr->next_elif->type;
curr->next_elif->flags |= EXPR_FOUND_TYPE;
if (!types_block(tr, &nexti->body)) {
@@ -1654,7 +1654,7 @@ static Status types_expr(Typer *tr, Expression *e) {
}
} break;
case EXPR_WHILE: {
- WhileExpr *w = &e->while_;
+ WhileExpr *w = e->while_;
bool ret = true;
if (w->cond && !types_expr(tr, w->cond))
ret = false;
@@ -2109,7 +2109,7 @@ static Status types_expr(Typer *tr, Expression *e) {
*t = *ret_type;
} break;
case EXPR_BLOCK: {
- Block *b = &e->block;
+ Block *b = e->block;
if (!types_block(tr, b))
return false;
if (b->ret_expr) {
@@ -2614,15 +2614,15 @@ static Status types_expr(Typer *tr, Expression *e) {
} break;
case EXPR_NMS: {
Namespace *prev_nms = tr->nms;
- tr->nms = &e->nms;
- e->nms.points_to = NULL;
- e->nms.body.flags |= BLOCK_IS_NMS;
- if (!types_block(tr, &e->nms.body)) {
+ Namespace *n = tr->nms = e->nms;
+ n->points_to = NULL;
+ n->body.flags |= BLOCK_IS_NMS;
+ if (!types_block(tr, &n->body)) {
tr->nms = prev_nms;
return false;
}
tr->nms = prev_nms;
- e->nms.associated_ident = NULL; /* set when we type the declaration */
+ n->associated_ident = NULL; /* set when we type the declaration which contains this namespace */
t->kind = TYPE_BUILTIN;
t->builtin = BUILTIN_NMS;
} break;
@@ -2819,7 +2819,7 @@ static Status types_decl(Typer *tr, Declaration *d) {
}
}
if (is_at_top_level)
- d->expr.nms.associated_ident = d->idents[0];
+ d->expr.nms->associated_ident = d->idents[0];
}
if (tr->nms && tr->block == &tr->nms->body) {
diff --git a/types.h b/types.h
index f3fa76c..d5a2b69 100644
--- a/types.h
+++ b/types.h
@@ -763,7 +763,7 @@ const char *const builtin_val_names[BUILTIN_VAL_COUNT] =
typedef struct Namespace {
Block body;
- Identifier associated_ident; /* if this is foo ::= nms { ... }, then associated_ident is foo; can be NULL */
+ Identifier associated_ident; /* if this is foo ::= nms { ... }, then associated_ident is foo; can be NULL. used by cgen. only non-null if the namespace isn't in a non-namespace block */
struct Namespace *points_to; /* if not NULL, this namespace just points to another namespace, because something has been included twice */
struct {
char *prefix; /* generated during sdecls_cgen */
@@ -815,17 +815,17 @@ typedef struct Expression {
} builtin;
Identifier ident;
NewExpr new;
- Namespace nms;
+ Namespace *nms;
struct {
Type type;
} del;
- IfExpr if_;
- WhileExpr while_;
+ IfExpr *if_;
+ WhileExpr *while_;
ForExpr *for_;
FnExpr *fn;
CastExpr cast;
SliceExpr slice;
- Block block;
+ Block *block;
struct Expression *tuple; /* dynamic array, even after typing */
Type typeval;
Value val;