move type enum out of struct
This commit is contained in:
parent
0d5313a063
commit
befce544e7
22
lex.c
22
lex.c
@ -81,9 +81,9 @@ TokList lex(const char *s, Pool *static_vars) {
|
||||
else if (streq_0_n("while", start, i))
|
||||
emit(&toks, &pos, (Tok){ .kind = TokWhile });
|
||||
else if (streq_0_n("true", start, i))
|
||||
emit(&toks, &pos, (Tok){ .kind = TokVal, .Val = { .type = { .kind = TypeBool, }, .Bool = true, }, });
|
||||
emit(&toks, &pos, (Tok){ .kind = TokVal, .Val = { .type = TypeBool, .Bool = true }});
|
||||
else if (streq_0_n("false", start, i))
|
||||
emit(&toks, &pos, (Tok){ .kind = TokVal, .Val = { .type = { .kind = TypeBool, }, .Bool = false, }, });
|
||||
emit(&toks, &pos, (Tok){ .kind = TokVal, .Val = { .type = TypeBool, .Bool = false }});
|
||||
else {
|
||||
emit(&toks, &pos, (Tok){
|
||||
.kind = TokIdent,
|
||||
@ -146,9 +146,7 @@ TokList lex(const char *s, Pool *static_vars) {
|
||||
emit(&toks, &pos, (Tok){
|
||||
.kind = TokVal,
|
||||
.Val = {
|
||||
.type = {
|
||||
.kind = TypeFloat,
|
||||
},
|
||||
.type = TypeFloat,
|
||||
.Float = num,
|
||||
},
|
||||
});
|
||||
@ -164,9 +162,7 @@ TokList lex(const char *s, Pool *static_vars) {
|
||||
emit(&toks, &pos, (Tok){
|
||||
.kind = TokVal,
|
||||
.Val = {
|
||||
.type = {
|
||||
.kind = TypeInt,
|
||||
},
|
||||
.type = TypeInt,
|
||||
.Int = num,
|
||||
},
|
||||
});
|
||||
@ -234,9 +230,9 @@ TokList lex(const char *s, Pool *static_vars) {
|
||||
case '!':
|
||||
consume(&pos, *(s++));
|
||||
if (s[0] == '=')
|
||||
emit(&toks, &pos, (Tok){ .kind = TokOp, .Op = OpNeq, });
|
||||
emit(&toks, &pos, (Tok){ .kind = TokOp, .Op = OpNeq });
|
||||
else {
|
||||
emit(&toks, &pos, (Tok){ .kind = TokOp, .Op = OpNot, });
|
||||
emit(&toks, &pos, (Tok){ .kind = TokOp, .Op = OpNot });
|
||||
continue;
|
||||
}
|
||||
break;
|
||||
@ -310,7 +306,7 @@ TokList lex(const char *s, Pool *static_vars) {
|
||||
set_err("Unclosed char literal");
|
||||
return toks;
|
||||
}
|
||||
emit(&toks, &pos, (Tok){ .kind = TokVal, .Val = { .type = { .kind = TypeChar, }, .Char = c, }, });
|
||||
emit(&toks, &pos, (Tok){ .kind = TokVal, .Val = { .type = TypeChar, .Char = c }});
|
||||
break;
|
||||
}
|
||||
case '"': {
|
||||
@ -348,10 +344,10 @@ TokList lex(const char *s, Pool *static_vars) {
|
||||
str[i] = c;
|
||||
}
|
||||
emit(&toks, &pos, (Tok){ .kind = TokVal, .Val = {
|
||||
.type.kind = TypeArr,
|
||||
.type = TypeArr,
|
||||
.Arr = {
|
||||
.is_string = true,
|
||||
.type.kind = TypeChar,
|
||||
.type = TypeChar,
|
||||
.vals = str,
|
||||
.len = size,
|
||||
.cap = size,
|
||||
|
22
main.c
22
main.c
@ -49,16 +49,16 @@ static void fn_putln(size_t extra_args, Value *args) {
|
||||
|
||||
static Value fn_int(Value *args) {
|
||||
Value ret = {
|
||||
.type.kind = TypeInt,
|
||||
.type = TypeInt,
|
||||
.Int = 0,
|
||||
};
|
||||
switch (args[0].type.kind) {
|
||||
switch (args[0].type) {
|
||||
case TypeVoid: break;
|
||||
case TypeFloat: ret.Int = (ssize_t)args[0].Float; break;
|
||||
case TypeInt: ret.Int = args[0].Int; break;
|
||||
case TypeBool: ret.Int = (ssize_t)args[0].Bool; break;
|
||||
case TypeArr:
|
||||
if (args[0].Arr.is_string && args[0].Arr.type.kind == TypeChar) {
|
||||
if (args[0].Arr.is_string && args[0].Arr.type == TypeChar) {
|
||||
ssize_t endpos;
|
||||
ret.Int = stoimax((char*)args[0].Arr.vals, args[0].Arr.len, 10, &endpos);
|
||||
if (endpos != -1) {
|
||||
@ -75,16 +75,16 @@ static Value fn_int(Value *args) {
|
||||
|
||||
static Value fn_float(Value *args) {
|
||||
Value ret = {
|
||||
.type.kind = TypeFloat,
|
||||
.type = TypeFloat,
|
||||
.Float = 0.0,
|
||||
};
|
||||
switch (args[0].type.kind) {
|
||||
switch (args[0].type) {
|
||||
case TypeVoid: break;
|
||||
case TypeFloat: ret.Float = args[0].Float; break;
|
||||
case TypeInt: ret.Float = (double)args[0].Int; break;
|
||||
case TypeBool: ret.Float = (double)args[0].Bool; break;
|
||||
case TypeArr:
|
||||
if (args[0].Arr.is_string && args[0].Arr.type.kind == TypeChar) {
|
||||
if (args[0].Arr.is_string && args[0].Arr.type == TypeChar) {
|
||||
ssize_t endpos;
|
||||
ret.Float = stod((char*)args[0].Arr.vals, args[0].Arr.len, &endpos);
|
||||
if (endpos != -1) {
|
||||
@ -100,18 +100,18 @@ static Value fn_float(Value *args) {
|
||||
}
|
||||
|
||||
static Value fn_pow(Value *args) {
|
||||
if (!(args[0].type.kind == TypeFloat && args[1].type.kind == TypeFloat)) {
|
||||
if (!(args[0].type == TypeFloat && args[1].type == TypeFloat)) {
|
||||
set_err("pow() requires arguments of type float");
|
||||
return (Value){0};
|
||||
}
|
||||
return (Value){
|
||||
.type.kind = TypeFloat,
|
||||
.type = TypeFloat,
|
||||
.Float = pow(args[0].Float, args[1].Float),
|
||||
};
|
||||
}
|
||||
|
||||
static void fn_sleep(Value *args) {
|
||||
if (!(args[0].type.kind == TypeFloat && args[0].Float >= 0.0)) {
|
||||
if (!(args[0].type == TypeFloat && args[0].Float >= 0.0)) {
|
||||
set_err("sleep() requires a positive float");
|
||||
return;
|
||||
}
|
||||
@ -135,10 +135,10 @@ static Value fn_getln(Value *args) {
|
||||
}
|
||||
|
||||
return (Value){
|
||||
.type.kind = TypeArr,
|
||||
.type = TypeArr,
|
||||
.Arr = {
|
||||
.is_string = true,
|
||||
.type.kind = TypeChar,
|
||||
.type = TypeChar,
|
||||
.vals = line,
|
||||
.len = len,
|
||||
.cap = cap,
|
||||
|
46
runtime.c
46
runtime.c
@ -8,7 +8,7 @@ Value eval_binary(IRInstr instr, const Value *lhs, const Value *rhs) {
|
||||
case IRSub:
|
||||
case IRMul:
|
||||
case IRDiv: {
|
||||
if (lhs->type.kind == TypeInt && rhs->type.kind == TypeInt) {
|
||||
if (lhs->type == TypeInt && rhs->type == TypeInt) {
|
||||
ssize_t res;
|
||||
switch (instr) {
|
||||
case IRAdd: res = lhs->Int + rhs->Int; break;
|
||||
@ -18,10 +18,10 @@ Value eval_binary(IRInstr instr, const Value *lhs, const Value *rhs) {
|
||||
default: ASSERT_UNREACHED();
|
||||
}
|
||||
return (Value){
|
||||
.type.kind = TypeInt,
|
||||
.type = TypeInt,
|
||||
.Int = res,
|
||||
};
|
||||
} else if (lhs->type.kind == TypeFloat && rhs->type.kind == TypeFloat) {
|
||||
} else if (lhs->type == TypeFloat && rhs->type == TypeFloat) {
|
||||
double res;
|
||||
switch (instr) {
|
||||
case IRAdd: res = lhs->Float + rhs->Float; break;
|
||||
@ -31,11 +31,11 @@ Value eval_binary(IRInstr instr, const Value *lhs, const Value *rhs) {
|
||||
default: ASSERT_UNREACHED();
|
||||
}
|
||||
return (Value){
|
||||
.type.kind = TypeFloat,
|
||||
.type = TypeFloat,
|
||||
.Float = res,
|
||||
};
|
||||
} else {
|
||||
set_err("Unsupported types for operation '%s': %s and %s", irinstr_str[instr], type_str[lhs->type.kind], type_str[rhs->type.kind]);
|
||||
set_err("Unsupported types for operation '%s': %s and %s", irinstr_str[instr], type_str[lhs->type], type_str[rhs->type]);
|
||||
return (Value){0};
|
||||
}
|
||||
}
|
||||
@ -44,7 +44,7 @@ Value eval_binary(IRInstr instr, const Value *lhs, const Value *rhs) {
|
||||
case IRLt:
|
||||
case IRLe: {
|
||||
bool res;
|
||||
if (lhs->type.kind == TypeInt && rhs->type.kind == TypeInt) {
|
||||
if (lhs->type == TypeInt && rhs->type == TypeInt) {
|
||||
switch (instr) {
|
||||
case IREq: res = lhs->Int == rhs->Int; break;
|
||||
case IRNeq: res = lhs->Int != rhs->Int; break;
|
||||
@ -52,7 +52,7 @@ Value eval_binary(IRInstr instr, const Value *lhs, const Value *rhs) {
|
||||
case IRLe: res = lhs->Int <= rhs->Int; break;
|
||||
default: ASSERT_UNREACHED();
|
||||
};
|
||||
} else if (lhs->type.kind == TypeFloat && rhs->type.kind == TypeFloat) {
|
||||
} else if (lhs->type == TypeFloat && rhs->type == TypeFloat) {
|
||||
switch (instr) {
|
||||
case IREq: res = lhs->Float == rhs->Float; break;
|
||||
case IRNeq: res = lhs->Float != rhs->Float; break;
|
||||
@ -60,8 +60,8 @@ Value eval_binary(IRInstr instr, const Value *lhs, const Value *rhs) {
|
||||
case IRLe: res = lhs->Float <= rhs->Float; break;
|
||||
default: ASSERT_UNREACHED();
|
||||
};
|
||||
} else if (lhs->type.kind == TypeArr && lhs->Arr.type.kind == TypeChar && lhs->Arr.is_string &&
|
||||
rhs->type.kind == TypeArr && rhs->Arr.type.kind == TypeChar && rhs->Arr.is_string) {
|
||||
} else if (lhs->type == TypeArr && lhs->Arr.type == TypeChar && lhs->Arr.is_string &&
|
||||
rhs->type == TypeArr && rhs->Arr.type == TypeChar && rhs->Arr.is_string) {
|
||||
switch (instr) {
|
||||
case IREq:
|
||||
res = lhs->Arr.len == rhs->Arr.len ? strncmp(lhs->Arr.vals, rhs->Arr.vals, lhs->Arr.len) == 0 : false;
|
||||
@ -74,23 +74,23 @@ Value eval_binary(IRInstr instr, const Value *lhs, const Value *rhs) {
|
||||
break;
|
||||
};
|
||||
} else {
|
||||
set_err("Unsupported types for operation '%s': %s and %s", irinstr_str[instr], type_str[lhs->type.kind], type_str[rhs->type.kind]);
|
||||
set_err("Unsupported types for operation '%s': %s and %s", irinstr_str[instr], type_str[lhs->type], type_str[rhs->type]);
|
||||
return (Value){0};
|
||||
}
|
||||
return (Value){
|
||||
.type.kind = TypeBool,
|
||||
.type = TypeBool,
|
||||
.Bool = res,
|
||||
};
|
||||
}
|
||||
case IRAnd:
|
||||
return (Value){
|
||||
.type.kind = TypeBool,
|
||||
.type = TypeBool,
|
||||
.Bool = is_nonzero(lhs) && is_nonzero(rhs),
|
||||
};
|
||||
break;
|
||||
case IROr:
|
||||
return (Value){
|
||||
.type.kind = TypeBool,
|
||||
.type = TypeBool,
|
||||
.Bool = is_nonzero(lhs) || is_nonzero(rhs),
|
||||
};
|
||||
break;
|
||||
@ -105,19 +105,19 @@ Value eval_unary(IRInstr instr, const Value *v) {
|
||||
case IRSet:
|
||||
return *v;
|
||||
case IRNeg:
|
||||
if (v->type.kind == TypeInt)
|
||||
return (Value){ .type.kind = TypeInt, .Int = -v->Int };
|
||||
else if (v->type.kind == TypeFloat)
|
||||
return (Value){ .type.kind = TypeFloat, .Float = -v->Float };
|
||||
if (v->type == TypeInt)
|
||||
return (Value){ .type = TypeInt, .Int = -v->Int };
|
||||
else if (v->type == TypeFloat)
|
||||
return (Value){ .type = TypeFloat, .Float = -v->Float };
|
||||
else {
|
||||
set_err("Unsupported type for operation '%s': %s", irinstr_str[instr], type_str[v->type.kind]);
|
||||
set_err("Unsupported type for operation '%s': %s", irinstr_str[instr], type_str[v->type]);
|
||||
return (Value){0};
|
||||
}
|
||||
case IRNot:
|
||||
if (v->type.kind == TypeBool) {
|
||||
return (Value){ .type.kind = TypeBool, .Bool = !v->Bool };
|
||||
if (v->type == TypeBool) {
|
||||
return (Value){ .type = TypeBool, .Bool = !v->Bool };
|
||||
} else {
|
||||
set_err("Unsupported type for operation '%s': %s", irinstr_str[instr], type_str[v->type.kind]);
|
||||
set_err("Unsupported type for operation '%s': %s", irinstr_str[instr], type_str[v->type]);
|
||||
return (Value){0};
|
||||
}
|
||||
case IRAddrOf:
|
||||
@ -129,7 +129,7 @@ Value eval_unary(IRInstr instr, const Value *v) {
|
||||
}
|
||||
|
||||
bool is_nonzero(const Value *v) {
|
||||
switch (v->type.kind) {
|
||||
switch (v->type) {
|
||||
case TypeInt: return v->Int != 0;
|
||||
case TypeFloat: return v->Float != 0.0;
|
||||
case TypeBool: return v->Bool;
|
||||
@ -140,7 +140,7 @@ bool is_nonzero(const Value *v) {
|
||||
Value zero_val(Type ty) {
|
||||
Value ret;
|
||||
ret.type = ty;
|
||||
switch (ty.kind) {
|
||||
switch (ty) {
|
||||
case TypeInt: ret.Int = 0; break;
|
||||
case TypeFloat: ret.Float = 0.0; break;
|
||||
case TypeBool: ret.Bool = false; break;
|
||||
|
8
tok.c
8
tok.c
@ -25,7 +25,7 @@ const char *type_str[TypeEnumSize] = {
|
||||
};
|
||||
|
||||
void print_value(const Value *v, bool raw) {
|
||||
switch (v->type.kind) {
|
||||
switch (v->type) {
|
||||
case TypeVoid:
|
||||
printf("(void)");
|
||||
break;
|
||||
@ -48,13 +48,13 @@ void print_value(const Value *v, bool raw) {
|
||||
}
|
||||
break;
|
||||
case TypePtr:
|
||||
printf("ptr<%s>(", type_str[v->Ptr.type.kind]);
|
||||
printf("ptr<%s>(", type_str[v->Ptr.type]);
|
||||
print_value(v->Ptr.val, false);
|
||||
printf(")");
|
||||
break;
|
||||
case TypeArr:
|
||||
if (v->Arr.is_string) {
|
||||
if (v->Arr.type.kind != TypeChar)
|
||||
if (v->Arr.type != TypeChar)
|
||||
ASSERT_UNREACHED();
|
||||
char *str = v->Arr.vals;
|
||||
if (!raw)
|
||||
@ -74,7 +74,7 @@ void print_value(const Value *v, bool raw) {
|
||||
} else {
|
||||
printf("[");
|
||||
for (size_t i = 0;; i++) {
|
||||
size_t ty_sz = type_size[v->Arr.type.kind];
|
||||
size_t ty_sz = type_size[v->Arr.type];
|
||||
Value ty_val = { .type = v->Arr.type };
|
||||
memcpy(&ty_val.Void, (uint8_t*)v->Arr.vals + ty_sz * i, ty_sz);
|
||||
print_value(&ty_val, false);
|
||||
|
28
tok.h
28
tok.h
@ -5,21 +5,17 @@
|
||||
|
||||
#include "util.h"
|
||||
|
||||
typedef struct Type {
|
||||
enum {
|
||||
TypeVoid = 0,
|
||||
TypeFloat,
|
||||
TypeInt,
|
||||
TypeBool,
|
||||
TypeChar,
|
||||
TypePtr,
|
||||
TypeArr,
|
||||
TypeEnumSize,
|
||||
} kind;
|
||||
|
||||
/*union {
|
||||
};*/
|
||||
} Type;
|
||||
enum Type {
|
||||
TypeVoid = 0,
|
||||
TypeFloat,
|
||||
TypeInt,
|
||||
TypeBool,
|
||||
TypeChar,
|
||||
TypePtr,
|
||||
TypeArr,
|
||||
TypeEnumSize,
|
||||
};
|
||||
typedef enum Type Type;
|
||||
|
||||
extern size_t type_size[TypeEnumSize];
|
||||
extern const char *type_str[TypeEnumSize];
|
||||
@ -38,8 +34,8 @@ typedef struct Value {
|
||||
struct Value *val;
|
||||
} Ptr;
|
||||
struct {
|
||||
bool is_string : 1;
|
||||
Type type;
|
||||
bool is_string : 1;
|
||||
void *vals;
|
||||
size_t len, cap;
|
||||
} Arr;
|
||||
|
Loading…
Reference in New Issue
Block a user