Aria

A low-level systems programming language
git clone git://git.m21c.me/Aria.git
Log | Files | Refs | LICENSE

commit 195442a2e5a780e9f0f8a5ac8ef738ec2d4e7869
parent 258c09122a8b198a6f881306f03680c3612ede87
Author: m21c  <ho*******@gmail.com>
Date:   Thu,  7 Oct 2021 19:07:01 +0200

implemented keyword-operators sizeof, alignof, lengthof and bitcast (not fully)

Diffstat:
Mcompiler.c | 111++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-----
1 file changed, 105 insertions(+), 6 deletions(-)

diff --git a/compiler.c b/compiler.c @@ -1852,6 +1852,7 @@ qualifiers(Source *source, int allowmask) f = QCONST, m = 0; break; + /* TODO(m21c): remove this */ case KVAR: f = QVAR, m = ~(QTYPE | QINFER); break; @@ -2493,9 +2494,16 @@ readatom(Source *source, int flags) case KALIGNOF: case KSIZEOF: + case KLENGTHOF: lhs = tokennode(source, NULL); gettok(source); - lhs->lhs = readatom(source, PRELAT); + if (getkind(source) == '(') { + gettok(source); + lhs->lhs = exprlist(source, false, NULL); + expect(source, ')', "expected ')'"); + } else { + lhs->lhs = readatom(source, 0); + } break; case KBITCAST: @@ -2504,7 +2512,7 @@ readatom(Source *source, int flags) expect(source, '(', "expected '('"); lhs->rhs = exprlist(source, false, NULL); expect(source, ')', "expected ')'"); - lhs->lhs = readatom(source, PRELAT); + lhs->lhs = readatom(source, 0); break; case KBREAK: @@ -2602,6 +2610,9 @@ readatom(Source *source, int flags) joinerror: error(getloc(source), "expected expression"); lhs = tokennode(source, NULL); + lhs->kind = 'N'; + lhs->type = prim + TERRTYPE; + lhs->u.u = 0; gettok(source); } @@ -3431,6 +3442,39 @@ typecheck(Env *env, Node *expr) expr->type->u.rtarget = rhs->type; return expr; + case KBITCAST: + assert(lhs); + assert(rhs); + + expr->lhs = lhs = typecheck(env, lhs); + + if (lhs->type->kind == TERRTYPE) + return expr->type = prim + TERRTYPE, expr; + + if (rhs->type->kind == TERRTYPE) + return expr->type = prim + TERRTYPE, expr; + + if (rhs->kind != 'T') { + error(&rhs->loc, "expected type"); + expr->type = prim + TERRTYPE; + return expr; + } + + expr->type = rhs->type; + return expr; + + case KSIZEOF: + case KALIGNOF: + case KLENGTHOF: + assert(lhs); + expr->lhs = lhs = typecheck(env, lhs); + + if (lhs->type->kind == TERRTYPE) + return expr->type = prim + TERRTYPE, expr; + + expr->type = prim + TUSIZE; + return expr; + default: return expr; } @@ -3590,6 +3634,14 @@ foldexpr(Env *env, Node *expr) return expr; + case ASCOPE: + assert(expr->lhs); + assert(expr->u.env); + + expr->lhs = foldexpr(expr->u.env, expr->lhs); + + return expr; + case ASTMT: rhs = expr; advancestmt: @@ -3607,11 +3659,32 @@ foldexpr(Env *env, Node *expr) expr->rhs = foldexpr(env, rhs); return expr; - case ASCOPE: - assert(expr->lhs); - assert(expr->u.env); + case KSIZEOF: + case KALIGNOF: + case KLENGTHOF: + assert(lhs); - expr->lhs = foldexpr(expr->u.env, expr->lhs); + expr->lhs = NULL; + if (expr->kind == KSIZEOF) { + expr->u.u = lhs->type->size; + + } else if (expr->kind == KALIGNOF) { + expr->u.u = lhs->type->align; + + } else /* if (expr->kind == KLENGTHOF) */ { + + /* TODO(m21c): add case for slice */ + if (lhs->type->kind == TARRAY) + expr->u.u = lhs->type->u.array.length; + else if (lhs->type->kind == TPTR) { + expr->u.u = 1; + } else { + expr->u.u = 0; + } + } + + /* delete(lhs); */ + expr->kind = 'N'; return expr; @@ -4261,6 +4334,32 @@ printexpr(FILE *out, Node *expr, int indent) n += printsubexpr(out, expr->rhs, false, indent); break; + case KSIZEOF: + case KALIGNOF: + case KLENGTHOF: + n += highlight(out, HLKEYWORD); + n += fprintf(out, "%s", nodestrings[expr->kind]); + n += highlight(out, HLDELIM); + n += fprintf(out, "("); + n += printexpr(out, expr->lhs, indent); + n += highlight(out, HLDELIM); + n += fprintf(out, ")"); + break; + + case KBITCAST: + n += highlight(out, HLKEYWORD); + n += fprintf(out, "bitcast"); + n += highlight(out, HLDELIM); + n += fprintf(out, "("); + n += highlight(out, HLTYPE); + n += printtype(out, expr->rhs->type, indent); + n += highlight(out, HLDELIM); + n += fprintf(out, ") ("); + n += printexpr(out, expr->lhs, indent); + n += highlight(out, HLDELIM); + n += fprintf(out, ")"); + break; + case KRETURN: n += highlight(out, HLKEYWORD); n += fprintf(out, "return ");