v2: short struct init syntax; .xxx enum checks; unions; assert
parent
c26016b132
commit
857cbfb0d2
|
@ -2522,8 +2522,8 @@ fn (p mut Parser) indot_expr() string {
|
||||||
if is_map && typ != 'string' {
|
if is_map && typ != 'string' {
|
||||||
p.error('bad element type: expecting `string`')
|
p.error('bad element type: expecting `string`')
|
||||||
}
|
}
|
||||||
T := p.table.find_type(arr_typ)
|
arr_typ2 := p.table.find_type(arr_typ)
|
||||||
if !is_map && !T.has_method('contains') {
|
if !is_map && !arr_typ2.has_method('contains') {
|
||||||
p.error('$arr_typ has no method `contains`')
|
p.error('$arr_typ has no method `contains`')
|
||||||
}
|
}
|
||||||
// `typ` is element's type
|
// `typ` is element's type
|
||||||
|
|
|
@ -109,7 +109,7 @@ int typ;
|
||||||
// Skip nameless enums
|
// Skip nameless enums
|
||||||
else if !no_name && !p.first_pass() {
|
else if !no_name && !p.first_pass() {
|
||||||
p.cgen.typedefs << 'typedef int $enum_name;'
|
p.cgen.typedefs << 'typedef int $enum_name;'
|
||||||
}
|
}
|
||||||
p.check(.rcbr)
|
p.check(.rcbr)
|
||||||
p.fgen_nl()
|
p.fgen_nl()
|
||||||
p.fgen_nl()
|
p.fgen_nl()
|
||||||
|
@ -122,18 +122,18 @@ fn (p mut Parser) check_enum_member_access() {
|
||||||
if p.expected_type.starts_with('Option_') {
|
if p.expected_type.starts_with('Option_') {
|
||||||
p.expected_type = p.expected_type[7..]
|
p.expected_type = p.expected_type[7..]
|
||||||
}
|
}
|
||||||
T := p.find_type(p.expected_type)
|
tt := p.find_type(p.expected_type)
|
||||||
if T.cat == .enum_ {
|
if tt.cat == .enum_ {
|
||||||
p.check(.dot)
|
p.check(.dot)
|
||||||
val := p.check_name()
|
val := p.check_name()
|
||||||
// Make sure this enum value exists
|
// Make sure this enum value exists
|
||||||
if !T.has_enum_val(val) {
|
if !tt.has_enum_val(val) {
|
||||||
p.error('enum `$T.name` does not have value `$val`')
|
p.error('enum `$tt.name` does not have value `$val`')
|
||||||
}
|
}
|
||||||
p.gen(mod_gen_name(T.mod) + '__' + p.expected_type + '_' + val)
|
p.gen(mod_gen_name(tt.mod) + '__' + p.expected_type + '_' + val)
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
p.error('`$T.name` is not an enum')
|
p.error('`$tt.name` is not an enum')
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -675,8 +675,8 @@ fn (p mut Parser) expression() string {
|
||||||
return typ
|
return typ
|
||||||
}
|
}
|
||||||
|
|
||||||
fn (p mut Parser) handle_operator(op string, typ string, cpostfix string, ph int, T &Type) {
|
fn (p mut Parser) handle_operator(op string, typ string,cpostfix string, ph int, tt &Type) {
|
||||||
if T.has_method(op) {
|
if tt.has_method(op) {
|
||||||
p.cgen.set_placeholder(ph, '${typ}_${cpostfix}(')
|
p.cgen.set_placeholder(ph, '${typ}_${cpostfix}(')
|
||||||
p.gen(')')
|
p.gen(')')
|
||||||
}
|
}
|
||||||
|
|
|
@ -1138,7 +1138,7 @@ fn (p mut Parser) fn_call_args(f mut Fn, generic_param_types []string) {
|
||||||
}
|
}
|
||||||
if i == 0 && (f.name == 'println' || f.name == 'print') && !(typ in ['string', 'ustring', 'void']) {
|
if i == 0 && (f.name == 'println' || f.name == 'print') && !(typ in ['string', 'ustring', 'void']) {
|
||||||
//
|
//
|
||||||
T := p.table.find_type(typ)
|
tt := p.table.find_type(typ)
|
||||||
$if !windows {
|
$if !windows {
|
||||||
$if !js {
|
$if !js {
|
||||||
fmt := p.typ_to_fmt(typ, 0)
|
fmt := p.typ_to_fmt(typ, 0)
|
||||||
|
@ -1156,31 +1156,31 @@ fn (p mut Parser) fn_call_args(f mut Fn, generic_param_types []string) {
|
||||||
}
|
}
|
||||||
// Make sure this type has a `str()` method
|
// Make sure this type has a `str()` method
|
||||||
$if !js {
|
$if !js {
|
||||||
if !T.has_method('str') {
|
if !tt.has_method('str') {
|
||||||
// varg
|
// varg
|
||||||
if T.name.starts_with('varg_') {
|
if tt.name.starts_with('varg_') {
|
||||||
p.gen_varg_str(T)
|
p.gen_varg_str(tt)
|
||||||
p.cgen.set_placeholder(ph, '${typ}_str(')
|
p.cgen.set_placeholder(ph, '${typ}_str(')
|
||||||
p.gen(')')
|
p.gen(')')
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
// Arrays have automatic `str()` methods
|
// Arrays have automatic `str()` methods
|
||||||
else if T.name.starts_with('array_') {
|
else if tt.name.starts_with('array_') {
|
||||||
p.gen_array_str(T)
|
p.gen_array_str(tt)
|
||||||
p.cgen.set_placeholder(ph, '${typ}_str(')
|
p.cgen.set_placeholder(ph, '${typ}_str(')
|
||||||
p.gen(')')
|
p.gen(')')
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
// struct
|
// struct
|
||||||
else if T.cat == .struct_ {
|
else if tt.cat == .struct_ {
|
||||||
p.gen_struct_str(T)
|
p.gen_struct_str(tt)
|
||||||
p.cgen.set_placeholder(ph, '${typ}_str(')
|
p.cgen.set_placeholder(ph, '${typ}_str(')
|
||||||
p.gen(')')
|
p.gen(')')
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
base := p.base_type(T.name)
|
base := p.base_type(tt.name)
|
||||||
if base != T.name {
|
if base != tt.name {
|
||||||
base_type := p.find_type(base)
|
base_type := p.find_type(base)
|
||||||
if base_type.has_method('str') {
|
if base_type.has_method('str') {
|
||||||
p.cgen.set_placeholder(ph, '${base_type.name}_str(')
|
p.cgen.set_placeholder(ph, '${base_type.name}_str(')
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/**********************************************************************
|
/**********************************************************************
|
||||||
*
|
*
|
||||||
* f32 to string
|
* f32 to string
|
||||||
*
|
*
|
||||||
* Copyright (c) 2019-2020 Dario Deledda. All rights reserved.
|
* Copyright (c) 2019-2020 Dario Deledda. All rights reserved.
|
||||||
* Use of this source code is governed by an MIT license
|
* Use of this source code is governed by an MIT license
|
||||||
|
@ -9,11 +9,11 @@
|
||||||
* This file contains the f32 to string functions
|
* This file contains the f32 to string functions
|
||||||
*
|
*
|
||||||
* These functions are based on the work of:
|
* These functions are based on the work of:
|
||||||
* Publication:PLDI 2018: Proceedings of the 39th ACM SIGPLAN
|
* Publication:PLDI 2018: Proceedings of the 39th ACM SIGPLAN
|
||||||
* Conference on Programming Language Design and ImplementationJune 2018
|
* Conference on Programming Language Design and ImplementationJune 2018
|
||||||
* Pages 270–282 https://doi.org/10.1145/3192366.3192369
|
* Pages 270–282 https://doi.org/10.1145/3192366.3192369
|
||||||
*
|
*
|
||||||
* inspired by the Go version here:
|
* inspired by the Go version here:
|
||||||
* https://github.com/cespare/ryu/tree/ba56a33f39e3bbbfa409095d0f9ae168a595feea
|
* https://github.com/cespare/ryu/tree/ba56a33f39e3bbbfa409095d0f9ae168a595feea
|
||||||
*
|
*
|
||||||
**********************************************************************/
|
**********************************************************************/
|
||||||
|
@ -72,7 +72,7 @@ fn (d Dec32) get_string_32(neg bool, n_digit int) string {
|
||||||
mut x := 0
|
mut x := 0
|
||||||
for x < (out_len-disp-1) {
|
for x < (out_len-disp-1) {
|
||||||
buf[y - x] = `0` + byte(out%10)
|
buf[y - x] = `0` + byte(out%10)
|
||||||
out /= 10
|
out /= 10
|
||||||
i++
|
i++
|
||||||
x++
|
x++
|
||||||
}
|
}
|
||||||
|
@ -170,7 +170,7 @@ pub fn f32_to_decimal(mant u32, exp u32) Dec32 {
|
||||||
mm_shift := bool_to_u32(mant != 0 || exp <= 1)
|
mm_shift := bool_to_u32(mant != 0 || exp <= 1)
|
||||||
mm := u32(4 * m2 - 1 - mm_shift)
|
mm := u32(4 * m2 - 1 - mm_shift)
|
||||||
|
|
||||||
mut vr := u32(0)
|
mut vr := u32(0)
|
||||||
mut vp := u32(0)
|
mut vp := u32(0)
|
||||||
mut vm := u32(0)
|
mut vm := u32(0)
|
||||||
mut e10 := 0
|
mut e10 := 0
|
||||||
|
@ -291,7 +291,7 @@ pub fn f32_to_decimal(mant u32, exp u32) Dec32 {
|
||||||
out = vr + bool_to_u32(vr == vm || last_removed_digit >= 5)
|
out = vr + bool_to_u32(vr == vm || last_removed_digit >= 5)
|
||||||
}
|
}
|
||||||
|
|
||||||
return Dec32{m: out, e: e10 + removed}
|
return Dec32{m: out e: e10 + removed}
|
||||||
}
|
}
|
||||||
|
|
||||||
// f32_to_str return a string in scientific notation with max n_digit after the dot
|
// f32_to_str return a string in scientific notation with max n_digit after the dot
|
||||||
|
@ -316,7 +316,7 @@ pub fn f32_to_str(f f32, n_digit int) string {
|
||||||
//println("with exp form")
|
//println("with exp form")
|
||||||
d = f32_to_decimal(mant, exp)
|
d = f32_to_decimal(mant, exp)
|
||||||
}
|
}
|
||||||
|
|
||||||
//println("${d.m} ${d.e}")
|
//println("${d.m} ${d.e}")
|
||||||
return d.get_string_32(neg, n_digit)
|
return d.get_string_32(neg, n_digit)
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,7 +28,7 @@ powers_of_10 = [
|
||||||
// We only need to find the length of at most 17 digit numbers.
|
// We only need to find the length of at most 17 digit numbers.
|
||||||
]
|
]
|
||||||
|
|
||||||
pow5_split_32 = [
|
pow5_split_32 = [
|
||||||
1152921504606846976, 1441151880758558720, 1801439850948198400, 2251799813685248000,
|
1152921504606846976, 1441151880758558720, 1801439850948198400, 2251799813685248000,
|
||||||
1407374883553280000, 1759218604441600000, 2199023255552000000, 1374389534720000000,
|
1407374883553280000, 1759218604441600000, 2199023255552000000, 1374389534720000000,
|
||||||
1717986918400000000, 2147483648000000000, 1342177280000000000, 1677721600000000000,
|
1717986918400000000, 2147483648000000000, 1342177280000000000, 1677721600000000000,
|
||||||
|
@ -55,8 +55,8 @@ pow5_inv_split_32 = [
|
||||||
]
|
]
|
||||||
|
|
||||||
pow5_split_64 =[
|
pow5_split_64 =[
|
||||||
Uint128{u64(0), 72057594037927936},
|
Uint128{0, 72057594037927936},
|
||||||
Uint128{u64(0), 90071992547409920},
|
Uint128{0, 90071992547409920},
|
||||||
Uint128{u64(0), 112589990684262400},
|
Uint128{u64(0), 112589990684262400},
|
||||||
Uint128{u64(0), 140737488355328000},
|
Uint128{u64(0), 140737488355328000},
|
||||||
Uint128{u64(0), 87960930222080000},
|
Uint128{u64(0), 87960930222080000},
|
||||||
|
@ -677,4 +677,4 @@ pow5_inv_split_64 = [
|
||||||
Uint128{8599192303405213841, 224711641857789488},
|
Uint128{8599192303405213841, 224711641857789488},
|
||||||
Uint128{14258051472207991719, 179769313486231590}
|
Uint128{14258051472207991719, 179769313486231590}
|
||||||
]
|
]
|
||||||
)
|
)
|
||||||
|
|
|
@ -16,7 +16,7 @@ CastExpr | EnumVal | Assoc | SizeOf | None | MapInit
|
||||||
pub type Stmt = VarDecl | GlobalDecl | FnDecl | Return | Module | Import | ExprStmt |
|
pub type Stmt = VarDecl | GlobalDecl | FnDecl | Return | Module | Import | ExprStmt |
|
||||||
ForStmt | StructDecl | ForCStmt | ForInStmt | CompIf | ConstDecl | Attr | BranchStmt |
|
ForStmt | StructDecl | ForCStmt | ForInStmt | CompIf | ConstDecl | Attr | BranchStmt |
|
||||||
HashStmt | AssignStmt | EnumDecl | TypeDecl | DeferStmt | GotoLabel | GotoStmt |
|
HashStmt | AssignStmt | EnumDecl | TypeDecl | DeferStmt | GotoLabel | GotoStmt |
|
||||||
LineComment | MultiLineComment
|
LineComment | MultiLineComment | AssertStmt
|
||||||
|
|
||||||
pub type Type = StructType | ArrayType
|
pub type Type = StructType | ArrayType
|
||||||
|
|
||||||
|
@ -469,6 +469,11 @@ pub:
|
||||||
expr Expr
|
expr Expr
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub struct AssertStmt {
|
||||||
|
pub:
|
||||||
|
expr Expr
|
||||||
|
}
|
||||||
|
|
||||||
pub struct Assoc {
|
pub struct Assoc {
|
||||||
pub:
|
pub:
|
||||||
name string
|
name string
|
||||||
|
|
|
@ -16,11 +16,12 @@ const (
|
||||||
)
|
)
|
||||||
|
|
||||||
pub struct Checker {
|
pub struct Checker {
|
||||||
table &table.Table
|
table &table.Table
|
||||||
mut:
|
mut:
|
||||||
file ast.File
|
file ast.File
|
||||||
nr_errors int
|
nr_errors int
|
||||||
errors []string
|
errors []string
|
||||||
|
expected_type table.Type
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn new_checker(table &table.Table) Checker {
|
pub fn new_checker(table &table.Table) Checker {
|
||||||
|
@ -78,6 +79,10 @@ pub fn (c mut Checker) check_struct_init(struct_init ast.StructInit) table.Type
|
||||||
}
|
}
|
||||||
.struct_ {
|
.struct_ {
|
||||||
info := typ_sym.info as table.Struct
|
info := typ_sym.info as table.Struct
|
||||||
|
if struct_init.fields.len == 0 {
|
||||||
|
// Short syntax TODO check
|
||||||
|
return struct_init.typ
|
||||||
|
}
|
||||||
if struct_init.exprs.len > info.fields.len {
|
if struct_init.exprs.len > info.fields.len {
|
||||||
c.error('too many fields', struct_init.pos)
|
c.error('too many fields', struct_init.pos)
|
||||||
}
|
}
|
||||||
|
@ -279,6 +284,7 @@ pub fn (c mut Checker) array_init(array_init mut ast.ArrayInit) table.Type {
|
||||||
// The first element's type
|
// The first element's type
|
||||||
if i == 0 {
|
if i == 0 {
|
||||||
elem_type = typ
|
elem_type = typ
|
||||||
|
c.expected_type = typ
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if !c.table.check(elem_type, typ) {
|
if !c.table.check(elem_type, typ) {
|
||||||
|
@ -366,15 +372,7 @@ pub fn (c mut Checker) expr(node ast.Expr) table.Type {
|
||||||
c.check_assign_expr(it)
|
c.check_assign_expr(it)
|
||||||
}
|
}
|
||||||
ast.EnumVal {
|
ast.EnumVal {
|
||||||
typ_idx := c.table.find_type_idx(it.enum_name) // or {
|
return c.enum_val(it)
|
||||||
typ := c.table.find_type(it.enum_name) or {
|
|
||||||
panic(err)
|
|
||||||
}
|
|
||||||
info := typ.info as table.Enum
|
|
||||||
if !(it.val in info.vals) {
|
|
||||||
c.error('enum `$it.enum_name` does not have a value `$it.val`', it.pos)
|
|
||||||
}
|
|
||||||
return typ_idx
|
|
||||||
}
|
}
|
||||||
ast.FloatLiteral {
|
ast.FloatLiteral {
|
||||||
return table.f64_type
|
return table.f64_type
|
||||||
|
@ -651,6 +649,20 @@ pub fn (c mut Checker) index_expr(node ast.IndexExpr) table.Type {
|
||||||
return typ
|
return typ
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// `.green` or `Color.green`
|
||||||
|
// If a short form is used, `expected_type` needs to be an enum
|
||||||
|
// with this value.
|
||||||
|
pub fn (c mut Checker) enum_val(node ast.EnumVal) table.Type {
|
||||||
|
typ_idx := if node.enum_name == '' { c.expected_type } else { c.table.find_type_idx(node.enum_name) }
|
||||||
|
typ := c.table.get_type_symbol(table.Type(typ_idx))
|
||||||
|
// println('checker: enum val $c.expected_type $typ.name')
|
||||||
|
info := typ.info as table.Enum
|
||||||
|
if !(node.val in info.vals) {
|
||||||
|
c.error('enum `$typ.name` does not have a value `$node.val`', node.pos)
|
||||||
|
}
|
||||||
|
return typ_idx
|
||||||
|
}
|
||||||
|
|
||||||
pub fn (c mut Checker) error(s string, pos token.Position) {
|
pub fn (c mut Checker) error(s string, pos token.Position) {
|
||||||
c.nr_errors++
|
c.nr_errors++
|
||||||
print_backtrace()
|
print_backtrace()
|
||||||
|
|
|
@ -238,6 +238,9 @@ pub fn (p mut Parser) top_stmt() ast.Stmt {
|
||||||
.key_enum {
|
.key_enum {
|
||||||
return p.enum_decl()
|
return p.enum_decl()
|
||||||
}
|
}
|
||||||
|
.key_union {
|
||||||
|
return p.struct_decl()
|
||||||
|
}
|
||||||
.line_comment {
|
.line_comment {
|
||||||
// p.next()
|
// p.next()
|
||||||
return ast.LineComment{
|
return ast.LineComment{
|
||||||
|
@ -252,7 +255,7 @@ pub fn (p mut Parser) top_stmt() ast.Stmt {
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
// #printf("");
|
// #printf("");
|
||||||
p.error('parser: bad top level statement')
|
p.error('parser: bad top level statement ' + p.tok.str())
|
||||||
return ast.Stmt{}
|
return ast.Stmt{}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -260,6 +263,13 @@ pub fn (p mut Parser) top_stmt() ast.Stmt {
|
||||||
|
|
||||||
pub fn (p mut Parser) stmt() ast.Stmt {
|
pub fn (p mut Parser) stmt() ast.Stmt {
|
||||||
match p.tok.kind {
|
match p.tok.kind {
|
||||||
|
.key_assert {
|
||||||
|
p.next()
|
||||||
|
expr,_ := p.expr(0)
|
||||||
|
return ast.AssertStmt{
|
||||||
|
expr: expr
|
||||||
|
}
|
||||||
|
}
|
||||||
.key_mut {
|
.key_mut {
|
||||||
return p.var_decl()
|
return p.var_decl()
|
||||||
}
|
}
|
||||||
|
@ -481,7 +491,7 @@ fn (p mut Parser) struct_init() ast.StructInit {
|
||||||
mut field_names := []string
|
mut field_names := []string
|
||||||
mut exprs := []ast.Expr
|
mut exprs := []ast.Expr
|
||||||
mut i := 0
|
mut i := 0
|
||||||
// TODO if sym.info is table.Struct
|
// TODO `if sym.info is table.Struct`
|
||||||
mut is_struct := false
|
mut is_struct := false
|
||||||
match sym.info {
|
match sym.info {
|
||||||
table.Struct {
|
table.Struct {
|
||||||
|
@ -489,25 +499,41 @@ fn (p mut Parser) struct_init() ast.StructInit {
|
||||||
}
|
}
|
||||||
else {}
|
else {}
|
||||||
}
|
}
|
||||||
|
is_short_syntax := !(p.peek_tok.kind == .colon || p.tok.kind == .rcbr) // `Vec{a,b,c}`
|
||||||
|
// p.warn(is_short_syntax.str())
|
||||||
for p.tok.kind != .rcbr {
|
for p.tok.kind != .rcbr {
|
||||||
field_name := p.check_name()
|
mut field_name := ''
|
||||||
field_names << field_name
|
if is_short_syntax {
|
||||||
|
expr,_ := p.expr(0)
|
||||||
|
exprs << expr
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
field_name = p.check_name()
|
||||||
|
field_names << field_name
|
||||||
|
}
|
||||||
// Set expected type for this field's expression
|
// Set expected type for this field's expression
|
||||||
// p.warn('$sym.name field $field_name')
|
// p.warn('$sym.name field $field_name')
|
||||||
if is_struct {
|
if is_struct {
|
||||||
info := sym.info as table.Struct
|
info := sym.info as table.Struct
|
||||||
field := sym.find_field(field_name) or {
|
if is_short_syntax {}
|
||||||
p.error('field `${sym.name}.$field_name` not found')
|
else {
|
||||||
continue
|
field := sym.find_field(field_name) or {
|
||||||
|
p.error('field `${sym.name}.$field_name` not found')
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
p.expected_type = field.typ
|
||||||
}
|
}
|
||||||
p.expected_type = field.typ
|
|
||||||
// p.warn('setting exp $field.typ')
|
// p.warn('setting exp $field.typ')
|
||||||
}
|
}
|
||||||
//
|
if !is_short_syntax {
|
||||||
p.check(.colon)
|
p.check(.colon)
|
||||||
expr,_ := p.expr(0)
|
expr,_ := p.expr(0)
|
||||||
exprs << expr
|
exprs << expr
|
||||||
|
}
|
||||||
i++
|
i++
|
||||||
|
if p.tok.kind == .comma {
|
||||||
|
p.check(.comma)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
node := ast.StructInit{
|
node := ast.StructInit{
|
||||||
typ: typ
|
typ: typ
|
||||||
|
@ -609,7 +635,8 @@ pub fn (p mut Parser) expr(precedence int) (ast.Expr,table.Type) {
|
||||||
}
|
}
|
||||||
.dot {
|
.dot {
|
||||||
// .enum_val
|
// .enum_val
|
||||||
node,typ = p.enum_val()
|
// node,typ = p.enum_val()
|
||||||
|
node = p.enum_val()
|
||||||
}
|
}
|
||||||
.chartoken {
|
.chartoken {
|
||||||
typ = table.byte_type
|
typ = table.byte_type
|
||||||
|
@ -909,14 +936,25 @@ fn (p &Parser) is_addative() bool {
|
||||||
*/
|
*/
|
||||||
// `.green`
|
// `.green`
|
||||||
// `pref.BuildMode.default_mode`
|
// `pref.BuildMode.default_mode`
|
||||||
fn (p mut Parser) enum_val() (ast.Expr,table.Type) {
|
fn (p mut Parser) enum_val() ast.EnumVal {
|
||||||
p.check(.dot)
|
p.check(.dot)
|
||||||
val := p.check_name()
|
val := p.check_name()
|
||||||
mut node := ast.Expr{}
|
/*
|
||||||
node = ast.EnumVal{
|
if p.expected_type == 0 {
|
||||||
|
p.error('wtf')
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
sym := p.table.get_type_symbol(p.expected_type) //or {
|
||||||
|
//return ast.EnumVal{val:val}
|
||||||
|
//}
|
||||||
|
p.warn(sym.name)
|
||||||
|
*/
|
||||||
|
|
||||||
|
return ast.EnumVal{
|
||||||
val: val
|
val: val
|
||||||
}
|
}
|
||||||
return node,table.int_type
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn (p mut Parser) for_statement() ast.Stmt {
|
fn (p mut Parser) for_statement() ast.Stmt {
|
||||||
|
@ -1332,12 +1370,18 @@ fn (p mut Parser) const_decl() ast.ConstDecl {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// structs and unions
|
||||||
fn (p mut Parser) struct_decl() ast.StructDecl {
|
fn (p mut Parser) struct_decl() ast.StructDecl {
|
||||||
is_pub := p.tok.kind == .key_pub
|
is_pub := p.tok.kind == .key_pub
|
||||||
if is_pub {
|
if is_pub {
|
||||||
p.next()
|
p.next()
|
||||||
}
|
}
|
||||||
p.check(.key_struct)
|
if p.tok.kind == .key_struct {
|
||||||
|
p.check(.key_struct)
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
p.check(.key_union)
|
||||||
|
}
|
||||||
is_c := p.tok.lit == 'C' && p.peek_tok.kind == .dot
|
is_c := p.tok.lit == 'C' && p.peek_tok.kind == .dot
|
||||||
if is_c {
|
if is_c {
|
||||||
p.next() // C
|
p.next() // C
|
||||||
|
|
|
@ -56,7 +56,7 @@ pub fn (t mut Table) register_global(name string, typ Type) {
|
||||||
// mod: p.mod
|
// mod: p.mod
|
||||||
// is_mut: true
|
// is_mut: true
|
||||||
// idx: -1
|
// idx: -1
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -186,7 +186,7 @@ pub fn (t &Table) get_type_symbol(typ Type) &TypeSymbol {
|
||||||
return &t.types[idx]
|
return &t.types[idx]
|
||||||
}
|
}
|
||||||
// this should never happen
|
// this should never happen
|
||||||
panic('get_type_symbol: invalid type $typ - $idx')
|
panic('get_type_symbol: invalid type $typ - ${idx}. This should neer happen')
|
||||||
}
|
}
|
||||||
|
|
||||||
// this will override or register builtin type
|
// this will override or register builtin type
|
||||||
|
|
Loading…
Reference in New Issue