Ast modified, Ast_Expr is not a union instead it uses inheritence
This commit is contained in:
@@ -70,39 +70,39 @@ gen_simple_decl(Ast_Resolved_Type *ast, Intern_String name){
|
||||
function void
|
||||
gen_expr(Ast_Expr *ast){
|
||||
switch(ast->kind){
|
||||
Ast_Begin(AST_IDENT, Ast_Expr){
|
||||
Ast_Begin(AST_IDENT, Ast_Atom){
|
||||
gen("%s", node->intern_val.str);
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_INT, Ast_Expr){
|
||||
Ast_Begin(AST_INT, Ast_Atom){
|
||||
gen("%lld", node->int_val);
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_STR, Ast_Expr){
|
||||
Ast_Begin(AST_STR, Ast_Atom){
|
||||
gen("LIT(\"%s\")", node->intern_val.str);
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_INDEX, Ast_Expr){
|
||||
gen_expr(node->index.expr);
|
||||
Ast_Begin(AST_INDEX, Ast_Index){
|
||||
gen_expr(node->expr);
|
||||
gen("[");
|
||||
gen_expr(node->index.index);
|
||||
gen_expr(node->index);
|
||||
gen("]");
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_UNARY, Ast_Expr){
|
||||
switch(node->unary.op){
|
||||
Ast_Begin(AST_UNARY, Ast_Unary){
|
||||
switch(node->op){
|
||||
case TK_Pointer: {
|
||||
gen("(*");
|
||||
gen_expr(node->unary.expr);
|
||||
gen_expr(node->expr);
|
||||
gen(")");
|
||||
} break;
|
||||
case TK_Dereference: {
|
||||
gen("(&");
|
||||
gen_expr(node->unary.expr);
|
||||
gen_expr(node->expr);
|
||||
gen(")");
|
||||
} break;
|
||||
invalid_default_case;
|
||||
@@ -110,38 +110,38 @@ gen_expr(Ast_Expr *ast){
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_CAST, Ast_Expr){
|
||||
Ast_Begin(AST_CAST, Ast_Cast){
|
||||
gen("(");
|
||||
gen("(");
|
||||
gen_simple_decl(node->cast.typespec->resolved_type, {});
|
||||
gen_simple_decl(node->typespec->resolved_type, {});
|
||||
gen(")");
|
||||
gen_expr(node->cast.expr);
|
||||
gen_expr(node->expr);
|
||||
gen(")");
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_COMPOUND, Ast_Expr){
|
||||
Ast_Begin(AST_COMPOUND, Ast_Compound){
|
||||
gen("(");
|
||||
gen_simple_decl(node->compound.type, {});
|
||||
gen_simple_decl(node->type, {});
|
||||
gen(")");
|
||||
|
||||
gen("{");
|
||||
For(node->compound.exprs){
|
||||
auto comp = it[0]->compound_item;
|
||||
if(comp.name){
|
||||
For(node->exprs){
|
||||
auto comp = it[0];
|
||||
if(comp->name){
|
||||
gen("[");
|
||||
gen_expr(comp.name);
|
||||
gen_expr(comp->name);
|
||||
gen("] = ");
|
||||
}
|
||||
if(comp.index){
|
||||
if(comp->index){
|
||||
gen("[");
|
||||
gen_expr(comp.index);
|
||||
gen_expr(comp->index);
|
||||
gen("] = ");
|
||||
}
|
||||
assert(comp.item);
|
||||
gen_expr(comp.item);
|
||||
assert(comp->item);
|
||||
gen_expr(comp->item);
|
||||
|
||||
if(!node->compound.exprs.is_last(it)) gen(", ");
|
||||
if(!node->exprs.is_last(it)) gen(", ");
|
||||
}
|
||||
gen("}");
|
||||
|
||||
@@ -182,10 +182,10 @@ gen_ast(Ast *ast){
|
||||
genln("");
|
||||
gen_simple_decl(lambda->ret->resolved_type, node->name);
|
||||
gen("(");
|
||||
For(lambda->params){
|
||||
assert(it[0]->kind == AST_LAMBDA_PARAM);
|
||||
gen_simple_decl(it[0]->lambda_param.typespec->resolved_type, it[0]->lambda_param.name);
|
||||
if(it != (lambda->params.end() - 1)) gen(", ");
|
||||
For(lambda->args){
|
||||
assert(it[0]->kind == AST_LAMBDA_ARG);
|
||||
gen_simple_decl(it[0]->typespec->resolved_type, it[0]->name);
|
||||
if(it != (lambda->args.end() - 1)) gen(", ");
|
||||
}
|
||||
gen(")");
|
||||
}
|
||||
@@ -224,8 +224,8 @@ test_gen(){
|
||||
sym_insert_builtins();
|
||||
eval_decl(result);
|
||||
gen(R"==(
|
||||
#define null_pointer 0
|
||||
#define null_lambda 0
|
||||
#define NULL_POINTER 0
|
||||
#define NULL_LAMBDA 0
|
||||
)==");
|
||||
gen_ast(result);
|
||||
__debugbreak();
|
||||
|
||||
137
new_ast.cpp
137
new_ast.cpp
@@ -73,7 +73,7 @@ enum Ast_Kind{
|
||||
AST_COMPOUND,
|
||||
|
||||
AST_LAMBDA,
|
||||
AST_LAMBDA_PARAM,
|
||||
AST_LAMBDA_ARG,
|
||||
AST_CONST,
|
||||
AST_VAR,
|
||||
|
||||
@@ -91,50 +91,59 @@ struct Ast{
|
||||
|
||||
struct Ast_Resolved_Type;
|
||||
struct Ast_Typespec;
|
||||
struct Ast_Expr:Ast{
|
||||
struct Ast_Expr:Ast{};
|
||||
|
||||
struct Ast_Atom: Ast_Expr{
|
||||
union{
|
||||
Intern_String intern_val;
|
||||
U64 int_val;
|
||||
struct{
|
||||
Token_Kind op;
|
||||
Ast_Expr *expr;
|
||||
}unary;
|
||||
struct{
|
||||
Token_Kind op;
|
||||
Ast_Expr *left;
|
||||
Ast_Expr *right;
|
||||
} binary;
|
||||
struct{
|
||||
Ast_Resolved_Type *type;
|
||||
Ast_Typespec *typespec;
|
||||
Array<Ast_Expr *> exprs;
|
||||
}compound;
|
||||
struct{
|
||||
};
|
||||
};
|
||||
|
||||
struct Ast_Compound_Item: Ast_Expr{
|
||||
Ast_Expr *name; // index | name
|
||||
Ast_Expr *index;
|
||||
Ast_Expr *item;
|
||||
}compound_item;
|
||||
struct{
|
||||
};
|
||||
|
||||
struct Ast_Compound: Ast_Expr{
|
||||
Ast_Resolved_Type *type;
|
||||
Ast_Typespec *typespec;
|
||||
Array<Ast_Compound_Item *> exprs;
|
||||
};
|
||||
|
||||
struct Ast_Unary: Ast_Expr{
|
||||
Token_Kind op;
|
||||
Ast_Expr *expr;
|
||||
};
|
||||
|
||||
struct Ast_Cast: Ast_Expr{
|
||||
Ast_Expr *expr;
|
||||
Ast_Typespec *typespec;
|
||||
}cast;
|
||||
struct{
|
||||
};
|
||||
|
||||
struct Ast_Index: Ast_Expr{
|
||||
Ast_Expr *expr;
|
||||
Ast_Expr *index;
|
||||
}index;
|
||||
struct{
|
||||
Intern_String name;
|
||||
Ast_Typespec *typespec;
|
||||
}lambda_param;
|
||||
};
|
||||
};
|
||||
|
||||
struct Ast_Binary: Ast_Expr{
|
||||
Token_Kind op;
|
||||
Ast_Expr *left;
|
||||
Ast_Expr *right;
|
||||
};
|
||||
|
||||
struct Ast_Block : Ast {
|
||||
Array<Ast *> stmts;
|
||||
};
|
||||
|
||||
struct Ast_Lambda_Arg: Ast_Expr{
|
||||
Intern_String name;
|
||||
Ast_Typespec *typespec;
|
||||
};
|
||||
|
||||
struct Ast_Lambda : Ast_Expr {
|
||||
Array<Ast_Expr *> params;
|
||||
Array<Ast_Lambda_Arg *> args;
|
||||
Ast_Typespec *ret;
|
||||
Ast_Block *block;
|
||||
};
|
||||
@@ -177,82 +186,82 @@ struct Ast_Package:Ast{
|
||||
result->pos = ipos; \
|
||||
result->id = ++pctx->unique_ids
|
||||
|
||||
function Ast_Expr *
|
||||
function Ast_Atom *
|
||||
ast_expr_string(Token *pos, Intern_String string){
|
||||
AST_NEW(Expr, AST_STR, pos);
|
||||
AST_NEW(Atom, AST_STR, pos);
|
||||
result->intern_val = string;
|
||||
return result;
|
||||
}
|
||||
|
||||
function Ast_Expr *
|
||||
function Ast_Atom *
|
||||
ast_expr_identifier(Token *pos, Intern_String string){
|
||||
AST_NEW(Expr, AST_IDENT, pos);
|
||||
AST_NEW(Atom, AST_IDENT, pos);
|
||||
result->intern_val = string;
|
||||
return result;
|
||||
}
|
||||
|
||||
function Ast_Expr *
|
||||
function Ast_Atom *
|
||||
ast_expr_integer(Token *pos, S64 integer){
|
||||
AST_NEW(Expr, AST_INT, pos);
|
||||
AST_NEW(Atom, AST_INT, pos);
|
||||
result->int_val = integer;
|
||||
return result;
|
||||
}
|
||||
|
||||
function Ast_Expr *
|
||||
ast_expr_binary(Ast_Expr *left, Ast_Expr *right, Token *op){
|
||||
AST_NEW(Expr, AST_BINARY, op);
|
||||
result->binary.op = op->kind;
|
||||
result->binary.left = left;
|
||||
result->binary.right = right;
|
||||
AST_NEW(Binary, AST_BINARY, op);
|
||||
result->op = op->kind;
|
||||
result->left = left;
|
||||
result->right = right;
|
||||
return result;
|
||||
}
|
||||
|
||||
function Ast_Expr *
|
||||
ast_expr_compound(Token *pos, Ast_Typespec *typespec, Array<Ast_Expr *> exprs){
|
||||
AST_NEW(Expr, AST_COMPOUND, pos);
|
||||
result->compound.typespec = typespec;
|
||||
result->compound.exprs = exprs.tight_copy(pctx->perm);
|
||||
function Ast_Compound *
|
||||
ast_expr_compound(Token *pos, Ast_Typespec *typespec, Array<Ast_Compound_Item *> exprs){
|
||||
AST_NEW(Compound, AST_COMPOUND, pos);
|
||||
result->typespec = typespec;
|
||||
result->exprs = exprs.tight_copy(pctx->perm);
|
||||
return result;
|
||||
}
|
||||
|
||||
function Ast_Expr *
|
||||
function Ast_Compound_Item *
|
||||
ast_expr_compound_item(Token *pos, Ast_Expr *index, Ast_Expr *name, Ast_Expr *item){
|
||||
AST_NEW(Expr, AST_COMPOUND_ITEM, pos);
|
||||
result->compound_item.name = name;
|
||||
result->compound_item.index = index;
|
||||
result->compound_item.item = item;
|
||||
AST_NEW(Compound_Item, AST_COMPOUND_ITEM, pos);
|
||||
result->name = name;
|
||||
result->index = index;
|
||||
result->item = item;
|
||||
return result;
|
||||
}
|
||||
|
||||
function Ast_Expr *
|
||||
ast_expr_cast(Token *pos, Ast_Expr *expr, Ast_Typespec *typespec){
|
||||
AST_NEW(Expr, AST_CAST, pos);
|
||||
result->cast.expr = expr;
|
||||
result->cast.typespec = typespec;
|
||||
AST_NEW(Cast, AST_CAST, pos);
|
||||
result->expr = expr;
|
||||
result->typespec = typespec;
|
||||
return result;
|
||||
}
|
||||
|
||||
function Ast_Expr *
|
||||
ast_expr_unary(Token *pos, Token_Kind op, Ast_Expr *expr){
|
||||
AST_NEW(Expr, AST_UNARY, pos);
|
||||
result->unary.expr = expr;
|
||||
result->unary.op = op;
|
||||
AST_NEW(Unary, AST_UNARY, pos);
|
||||
result->expr = expr;
|
||||
result->op = op;
|
||||
return result;
|
||||
}
|
||||
|
||||
function Ast_Expr *
|
||||
ast_expr_index(Token *pos, Ast_Expr *expr, Ast_Expr *index){
|
||||
AST_NEW(Expr, AST_INDEX, pos);
|
||||
result->index.expr = expr;
|
||||
result->index.index = index;
|
||||
AST_NEW(Index, AST_INDEX, pos);
|
||||
result->expr = expr;
|
||||
result->index = index;
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
function Ast_Lambda *
|
||||
ast_lambda(Token *pos, Array<Ast_Expr *> params, Ast_Typespec *ret){
|
||||
ast_lambda(Token *pos, Array<Ast_Lambda_Arg *> params, Ast_Typespec *ret){
|
||||
AST_NEW(Lambda, AST_LAMBDA, pos);
|
||||
result->params = params.tight_copy(pctx->perm);
|
||||
result->args = params.tight_copy(pctx->perm);
|
||||
result->ret = ret;
|
||||
return result;
|
||||
}
|
||||
@@ -263,11 +272,11 @@ ast_expr_lambda_empty(Token *pos){
|
||||
return result;
|
||||
}
|
||||
|
||||
function Ast_Expr *
|
||||
ast_expr_lambda_param(Token *pos, Intern_String name, Ast_Typespec *typespec){
|
||||
AST_NEW(Expr, AST_LAMBDA_PARAM, pos);
|
||||
result->lambda_param.name = name;
|
||||
result->lambda_param.typespec = typespec;
|
||||
function Ast_Lambda_Arg *
|
||||
ast_expr_lambda_arg(Token *pos, Intern_String name, Ast_Typespec *typespec){
|
||||
AST_NEW(Lambda_Arg, AST_LAMBDA_ARG, pos);
|
||||
result->name = name;
|
||||
result->typespec = typespec;
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
@@ -124,11 +124,11 @@ Compound literals
|
||||
function Ast_Expr *parse_expr(S64 rbp = 0);
|
||||
function Ast_Typespec *parse_typespec();
|
||||
|
||||
function Ast_Expr *
|
||||
function Ast_Compound *
|
||||
parse_expr_compound(){
|
||||
Scratch scratch;
|
||||
Token *pos = token_get();
|
||||
Array<Ast_Expr *> exprs = {scratch};
|
||||
Array<Ast_Compound_Item *> exprs = {scratch};
|
||||
while(!token_is(TK_CloseBrace)){
|
||||
Token *token = token_get();
|
||||
Ast_Expr *index = 0;
|
||||
@@ -145,7 +145,7 @@ parse_expr_compound(){
|
||||
}
|
||||
|
||||
Ast_Expr *item = parse_expr();
|
||||
Ast_Expr *item_comp = ast_expr_compound_item(token, index, name, item);
|
||||
Ast_Compound_Item *item_comp = ast_expr_compound_item(token, index, name, item);
|
||||
exprs.add(item_comp);
|
||||
|
||||
if(!token_match(TK_Comma)){
|
||||
@@ -154,7 +154,7 @@ parse_expr_compound(){
|
||||
}
|
||||
token_expect(TK_CloseBrace);
|
||||
|
||||
Ast_Expr *result = ast_expr_compound(pos, 0, exprs);
|
||||
Ast_Compound *result = ast_expr_compound(pos, 0, exprs);
|
||||
return result;
|
||||
}
|
||||
|
||||
@@ -179,7 +179,7 @@ parse_block(){
|
||||
function Ast_Lambda *
|
||||
parse_lambda(Token *token, B32 is_typespec = false){ // @Todo(Krzosa): is_typespec is not used currently
|
||||
Scratch scratch;
|
||||
Array<Ast_Expr *> params = {scratch};
|
||||
Array<Ast_Lambda_Arg *> params = {scratch};
|
||||
// @Note(Krzosa): No need to guard against "()"
|
||||
// We needed to lookahead to verify it's a function
|
||||
// and this routine only fires when we have situation
|
||||
@@ -188,7 +188,7 @@ parse_lambda(Token *token, B32 is_typespec = false){ // @Todo(Krzosa): is_typesp
|
||||
Token *name = token_expect(TK_Identifier);
|
||||
token_expect(TK_Colon);
|
||||
Ast_Typespec *typespec = parse_typespec();
|
||||
Ast_Expr *param = ast_expr_lambda_param(name, name->intern_val, typespec);
|
||||
Ast_Lambda_Arg *param = ast_expr_lambda_arg(name, name->intern_val, typespec);
|
||||
params.add(param);
|
||||
|
||||
if(!token_match(TK_Comma)){
|
||||
@@ -296,34 +296,6 @@ parse_expr(S64 rbp){
|
||||
return left;
|
||||
}
|
||||
|
||||
function S64
|
||||
expr_eval(Ast_Expr *expr){
|
||||
switch(expr->kind){
|
||||
case AST_INT: return expr->int_val;
|
||||
case AST_UNARY:{
|
||||
S64 value = expr_eval(expr->unary.expr);
|
||||
switch(expr->unary.op){
|
||||
case TK_PostDecrement: return value - 1;
|
||||
case TK_PostIncrement: return value + 1;
|
||||
default: invalid_codepath;
|
||||
}
|
||||
}break;
|
||||
case AST_BINARY : {
|
||||
S64 left = expr_eval(expr->binary.left);
|
||||
S64 right = expr_eval(expr->binary.right);
|
||||
switch(expr->binary.op){
|
||||
case TK_Add: return left + right;
|
||||
case TK_Sub: return left - right;
|
||||
case TK_Mul: return left * right;
|
||||
case TK_Div: return left / right;
|
||||
default: invalid_codepath;
|
||||
}
|
||||
}break;
|
||||
default: invalid_codepath;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
#define TEST_PARSER() \
|
||||
Scratch scratch(thread_ctx.scratch); \
|
||||
Parse_Ctx ctx = {}; \
|
||||
@@ -334,20 +306,20 @@ function void
|
||||
test_parse_expr(){
|
||||
TEST_PARSER();
|
||||
struct Test{String str;S64 val;};
|
||||
Array<Test> exprs = {scratch};
|
||||
// Array<Test> exprs = {scratch};
|
||||
//exprs.add({"thing[1][2][3]"_s, 0});
|
||||
exprs.add({"4++++--"_s, 5});
|
||||
exprs.add({"(4+5)*2"_s, (4+5)*2});
|
||||
exprs.add({"4+5*2"_s, 4+5*2});
|
||||
exprs.add({"4*5+5"_s, 4*5+5});
|
||||
exprs.add({"4+5+5+3"_s, 4+5+5+3});
|
||||
// exprs.add({"4++++--"_s, 5});
|
||||
// exprs.add({"(4+5)*2"_s, (4+5)*2});
|
||||
// exprs.add({"4+5*2"_s, 4+5*2});
|
||||
// exprs.add({"4*5+5"_s, 4*5+5});
|
||||
// exprs.add({"4+5+5+3"_s, 4+5+5+3});
|
||||
|
||||
For(exprs){
|
||||
lex_restream(&ctx, it->str, "test_expr"_s);
|
||||
Ast_Expr *result = parse_expr();
|
||||
S64 val = expr_eval(result);
|
||||
assert(val == it->val);
|
||||
}
|
||||
// For(exprs){
|
||||
// lex_restream(&ctx, it->str, "test_expr"_s);
|
||||
// Ast_Expr *result = parse_expr();
|
||||
// S64 val = expr_eval(result);
|
||||
// assert(val == it->val);
|
||||
// }
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
@@ -112,9 +112,9 @@ eval_typespec(Ast_Typespec *ast){
|
||||
Ast_Begin(AST_TYPESPEC_LAMBDA, Ast_Typespec){
|
||||
Scratch scratch;
|
||||
Ast_Resolved_Type *ret = eval_typespec(node->lambda->ret);
|
||||
Array<Ast_Resolved_Type *> params = {scratch};
|
||||
For(node->lambda->params) params.add(eval_typespec(it[0]->lambda_param.typespec));
|
||||
node->resolved_type = type_lambda(ret, params);
|
||||
Array<Ast_Resolved_Type *> args = {scratch};
|
||||
For(node->lambda->args) args.add(eval_typespec(it[0]->typespec));
|
||||
node->resolved_type = type_lambda(ret, args);
|
||||
return node->resolved_type;
|
||||
Ast_End();
|
||||
}
|
||||
@@ -161,19 +161,19 @@ resolve_type_pair(Token *pos, Ast_Resolved_Type *a, Ast_Resolved_Type *b){
|
||||
function Operand
|
||||
eval_expr(Ast_Expr *ast, Ast_Resolved_Type *expected_type){
|
||||
switch(ast->kind){
|
||||
Ast_Begin(AST_INT, Ast_Expr){
|
||||
Ast_Begin(AST_INT, Ast_Atom){
|
||||
Operand result = {type_int, true, {.int_val=(S64)node->int_val}};
|
||||
return result;
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_STR, Ast_Expr){
|
||||
Ast_Begin(AST_STR, Ast_Atom){
|
||||
Operand result = {type_string, true, {.intern_val = node->intern_val}};
|
||||
return result;
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_IDENT, Ast_Expr){
|
||||
Ast_Begin(AST_IDENT, Ast_Atom){
|
||||
Sym *sym = sym_get(node->intern_val);
|
||||
if(!sym){
|
||||
parsing_error(node->pos, "Identifier is undefined");
|
||||
@@ -193,12 +193,12 @@ eval_expr(Ast_Expr *ast, Ast_Resolved_Type *expected_type){
|
||||
else if(expected_type->kind == TYPE_Pointer){
|
||||
result.int_val = 0;
|
||||
node->kind = AST_IDENT;
|
||||
node->intern_val = pctx->intern("null_pointer"_s);
|
||||
node->intern_val = pctx->intern("NULL_POINTER"_s);
|
||||
}
|
||||
else if(expected_type->kind == TYPE_Lambda){
|
||||
result.int_val = 0;
|
||||
node->kind = AST_IDENT;
|
||||
node->intern_val = pctx->intern("null_lambda"_s);
|
||||
node->intern_val = pctx->intern("NULL_LAMBDA"_s);
|
||||
}
|
||||
else if(expected_type == type_bool){
|
||||
result.int_val = 0;
|
||||
@@ -228,9 +228,9 @@ eval_expr(Ast_Expr *ast, Ast_Resolved_Type *expected_type){
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_INDEX, Ast_Expr){
|
||||
Operand left = eval_expr(node->index.expr);
|
||||
Operand index = eval_expr(node->index.index);
|
||||
Ast_Begin(AST_INDEX, Ast_Index){
|
||||
Operand left = eval_expr(node->expr);
|
||||
Operand index = eval_expr(node->index);
|
||||
if(left.type->kind != TYPE_Array) parsing_error(node->pos, "Indexing variable that is not an array");
|
||||
if(index.type != type_int) parsing_error(node->pos, "Trying to index the array with invalid type, expected int");
|
||||
Operand result = {left.type->arr.base};
|
||||
@@ -238,30 +238,30 @@ eval_expr(Ast_Expr *ast, Ast_Resolved_Type *expected_type){
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_COMPOUND, Ast_Expr){
|
||||
Ast_Resolved_Type *type = eval_typespec(node->compound.typespec);
|
||||
Ast_Begin(AST_COMPOUND, Ast_Compound){
|
||||
Ast_Resolved_Type *type = eval_typespec(node->typespec);
|
||||
Ast_Resolved_Type *variable_type = expected_type;
|
||||
if(!type && variable_type) type = variable_type;
|
||||
else if(!variable_type && type);
|
||||
else if(variable_type != type) parsing_error(node->pos, "Variable type different from explicit compound type");
|
||||
node->compound.type = type;
|
||||
node->type = type;
|
||||
|
||||
if(type->kind == TYPE_Array){
|
||||
if(node->compound.exprs.len > type->arr.size) parsing_error(node->pos, "compound statement has too many items for this type");
|
||||
if(node->exprs.len > type->arr.size) parsing_error(node->pos, "compound statement has too many items for this type");
|
||||
Ast_Resolved_Type *item_type = type->arr.base;
|
||||
|
||||
For(node->compound.exprs){
|
||||
For(node->exprs){
|
||||
assert(it[0]->kind == AST_COMPOUND_ITEM);
|
||||
Ast_Expr *i = (Ast_Expr *)it[0];
|
||||
Ast_Compound_Item *i = (Ast_Compound_Item *)it[0];
|
||||
assert(i->kind == AST_COMPOUND_ITEM);
|
||||
if(i->compound_item.name) parsing_error(i->pos, "Invalid indexing kind in a compound expression of type %s", type_names[type->kind]);
|
||||
if(i->compound_item.index){
|
||||
Operand index_op = eval_expr(i->compound_item.index);
|
||||
if(i->name) parsing_error(i->pos, "Invalid indexing kind in a compound expression of type %s", type_names[type->kind]);
|
||||
if(i->index){
|
||||
Operand index_op = eval_expr(i->index);
|
||||
if(!index_op.is_const) parsing_error(i->pos, "Index in a compound expression is not a constant");
|
||||
if(index_op.type != type_int) parsing_error(i->pos, "Index should be of type int");
|
||||
if(index_op.int_val > (type->arr.size - 1)) parsing_error(i->pos, "Invalid index in compound expression, larger then type can store");
|
||||
}
|
||||
Operand expr = eval_expr(i->compound_item.item, item_type);
|
||||
Operand expr = eval_expr(i->item, item_type);
|
||||
resolve_type_pair(i->pos, expr.type, item_type);
|
||||
}
|
||||
}
|
||||
@@ -272,9 +272,9 @@ eval_expr(Ast_Expr *ast, Ast_Resolved_Type *expected_type){
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_CAST, Ast_Expr){
|
||||
Operand expr = eval_expr(node->cast.expr);
|
||||
Ast_Resolved_Type *type = eval_typespec(node->cast.typespec);
|
||||
Ast_Begin(AST_CAST, Ast_Cast){
|
||||
Operand expr = eval_expr(node->expr);
|
||||
Ast_Resolved_Type *type = eval_typespec(node->typespec);
|
||||
|
||||
if(type == expr.type) return expr;
|
||||
|
||||
@@ -298,9 +298,9 @@ eval_expr(Ast_Expr *ast, Ast_Resolved_Type *expected_type){
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_UNARY, Ast_Expr){
|
||||
Operand value = eval_expr(node->unary.expr);
|
||||
switch(node->unary.op){
|
||||
Ast_Begin(AST_UNARY, Ast_Unary){
|
||||
Operand value = eval_expr(node->expr);
|
||||
switch(node->op){
|
||||
case TK_Pointer:{
|
||||
if(value.type->kind != TYPE_Pointer) parsing_error(node->pos, "Dereferencing a value that is not a pointer");
|
||||
Operand result = {value.type->base};
|
||||
@@ -316,15 +316,15 @@ eval_expr(Ast_Expr *ast, Ast_Resolved_Type *expected_type){
|
||||
Ast_End();
|
||||
}
|
||||
|
||||
Ast_Begin(AST_BINARY, Ast_Expr){
|
||||
Operand left = eval_expr(ast->binary.left);
|
||||
Operand right = eval_expr(ast->binary.right);
|
||||
Ast_Begin(AST_BINARY, Ast_Binary){
|
||||
Operand left = eval_expr(node->left);
|
||||
Operand right = eval_expr(node->right);
|
||||
Operand result = {};
|
||||
result.type = resolve_type_pair(node->pos, left.type, right.type);
|
||||
if(left.is_const && right.is_const){
|
||||
result.is_const = true;
|
||||
if(result.type == type_int){
|
||||
switch(node->binary.op){
|
||||
switch(node->op){
|
||||
case TK_Add: result.int_val = left.int_val + right.int_val; break;
|
||||
case TK_Sub: result.int_val = left.int_val - right.int_val; break;
|
||||
case TK_Mul: result.int_val = left.int_val * right.int_val; break;
|
||||
|
||||
Reference in New Issue
Block a user