Add Core compiler interface
This commit is contained in:
73
base.cpp
73
base.cpp
@@ -138,6 +138,7 @@ typedef double F64;
|
||||
#define JOIN(X,Y) JOIN1(X,Y)
|
||||
#define string_expand(x) (int)x.len, x.str
|
||||
|
||||
#define CORE_STRINGS
|
||||
struct String{
|
||||
U8 *str;
|
||||
S64 len;
|
||||
@@ -154,78 +155,6 @@ global String string_null = {(U8 *)"null", 4};
|
||||
#include "stb_sprintf.h"
|
||||
#define snprintf stbsp_snprintf
|
||||
|
||||
|
||||
union Vec2 {
|
||||
struct { F32 x, y; };
|
||||
struct { F32 width, height; };
|
||||
F32 p[2];
|
||||
};
|
||||
|
||||
union Vec3 {
|
||||
struct{ F32 x, y, z; };
|
||||
struct{ F32 r, g, b; };
|
||||
struct{ Vec2 xy; F32 z_; };
|
||||
struct{ F32 x_; Vec2 yz; };
|
||||
F32 p[3];
|
||||
};
|
||||
|
||||
union Vec4 {
|
||||
struct{ F32 x, y, z, w; };
|
||||
struct{ F32 r, g, b, a; };
|
||||
struct{ Vec2 xy; Vec2 zw; };
|
||||
struct{ Vec2 xy_; F32 width, height; };
|
||||
struct{ Vec3 xyz; F32 w_; };
|
||||
struct{ F32 x_; Vec3 yzw; };
|
||||
struct{ Vec3 rgb; F32 a_; };
|
||||
F32 p[4];
|
||||
};
|
||||
|
||||
struct Mat4 {
|
||||
F32 p[4][4];
|
||||
};
|
||||
|
||||
union Vec1I {
|
||||
S32 x;
|
||||
S32 p[1];
|
||||
};
|
||||
|
||||
union Vec2I {
|
||||
struct { S32 x, y; };
|
||||
struct { S32 width, height; };
|
||||
S32 p[2];
|
||||
};
|
||||
|
||||
union Vec3I {
|
||||
struct { S32 x, y, z; };
|
||||
struct { S32 r, g, b; };
|
||||
struct { Vec2I xy; S32 z_; };
|
||||
struct { S32 x_; Vec2I yz; };
|
||||
S32 p[3];
|
||||
};
|
||||
|
||||
union Vec4I {
|
||||
struct { S32 x, y, z, w; };
|
||||
struct { S32 r, g, b, a; };
|
||||
struct { Vec2I xy; Vec2I zw; };
|
||||
struct { Vec2I xy_; S32 width, height; };
|
||||
struct { Vec3I xyz; S32 w_; };
|
||||
struct { S32 x_; Vec3I yzw; };
|
||||
struct { Vec3I rgb; S32 a_; };
|
||||
S32 p[4];
|
||||
};
|
||||
|
||||
union Rect2 {
|
||||
struct {F32 min_x, min_y, max_x, max_y;};
|
||||
struct { Vec2 min; Vec2 max; };
|
||||
F32 p[4];
|
||||
};
|
||||
|
||||
union Rect2I {
|
||||
struct { S32 min_x, min_y, max_x, max_y;};
|
||||
struct { Vec2I min; Vec2I max; };
|
||||
S32 p[4];
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Utilities
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
1714
base_math.cpp
1714
base_math.cpp
File diff suppressed because it is too large
Load Diff
@@ -5,7 +5,7 @@ rem cl main.cpp -I.. user32.lib
|
||||
clang core_main.cpp -O0 -Wall -Wno-unused-function -fno-exceptions -fdiagnostics-absolute-paths -g -o main.exe -Wl,user32.lib
|
||||
rem ubuntu run clang core_main.cpp -O0 -Wall -Wno-unused-function -fno-exceptions -fdiagnostics-absolute-paths -g -o core.out
|
||||
|
||||
main.exe -testing
|
||||
rem main.exe -testing
|
||||
|
||||
rem echo Building arms race
|
||||
rem call examples/arms_race/build_arms_race.bat
|
||||
|
||||
@@ -1,13 +1,4 @@
|
||||
struct Token;
|
||||
struct BigInt
|
||||
{
|
||||
unsigned digit_count;
|
||||
bool is_negative;
|
||||
union {
|
||||
uint64_t digit;
|
||||
uint64_t *digits;
|
||||
};
|
||||
};
|
||||
|
||||
#include <inttypes.h>
|
||||
enum CmpRes
|
||||
|
||||
327
core_ast.cpp
327
core_ast.cpp
@@ -1,332 +1,5 @@
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// AST
|
||||
//-----------------------------------------------------------------------------
|
||||
enum Ast_Kind: U32{
|
||||
AST_NONE,
|
||||
|
||||
AST_NAMESPACE,
|
||||
|
||||
AST_MODULE,
|
||||
AST_FILE,
|
||||
AST_SCOPE,
|
||||
AST_VALUE,
|
||||
AST_CAST,
|
||||
AST_IDENT,
|
||||
AST_INDEX,
|
||||
AST_UNARY,
|
||||
AST_BINARY,
|
||||
AST_CALL_ITEM,
|
||||
AST_CALL,
|
||||
|
||||
AST_CONSTANT_ASSERT,
|
||||
AST_RUNTIME_ASSERT,
|
||||
AST_SIZE_OF,
|
||||
AST_LENGTH_OF,
|
||||
AST_ALIGN_OF,
|
||||
AST_TYPE_OF,
|
||||
|
||||
AST_SWITCH,
|
||||
AST_SWITCH_CASE,
|
||||
AST_VAR_UNPACK,
|
||||
AST_BREAK,
|
||||
AST_COMPOUND,
|
||||
AST_TYPE,
|
||||
AST_VAR,
|
||||
AST_CONST,
|
||||
AST_POINTER,
|
||||
AST_ARRAY,
|
||||
AST_FOR,
|
||||
AST_IF,
|
||||
AST_IF_NODE,
|
||||
AST_RETURN,
|
||||
AST_BLOCK,
|
||||
AST_PASS,
|
||||
AST_LAMBDA,
|
||||
AST_LAMBDA_EXPR,
|
||||
AST_LAMBDA_ARG,
|
||||
AST_ENUM,
|
||||
AST_ENUM_MEMBER,
|
||||
AST_STRUCT,
|
||||
};
|
||||
|
||||
typedef U32 Ast_Flag;
|
||||
enum{
|
||||
AST_EXPR = bit_flag(1),
|
||||
AST_STMT = bit_flag(2),
|
||||
AST_STRICT = bit_flag(3),
|
||||
AST_AGGREGATE = bit_flag(4),
|
||||
AST_AGGREGATE_CHILD = bit_flag(5),
|
||||
AST_ATOM = bit_flag(7),
|
||||
AST_FOREIGN = bit_flag(8),
|
||||
AST_DECL = bit_flag(9),
|
||||
AST_GLOBAL = bit_flag(10),
|
||||
AST_FLAG = bit_flag(11),
|
||||
AST_VAR_IS_CONST = bit_flag(12),
|
||||
AST_OPERATOR_OVERLOAD = bit_flag(13),
|
||||
AST_IS_LVALUE = bit_flag(14),
|
||||
};
|
||||
|
||||
struct Ast{
|
||||
U64 di; // Debug id, shouldn't ever be used in the program
|
||||
Token *pos;
|
||||
|
||||
Ast_Kind kind;
|
||||
Ast_Scope *parent_scope;
|
||||
Ast_Flag flags;
|
||||
};
|
||||
|
||||
struct Ast_Type;
|
||||
struct Ast_Expr:Ast{
|
||||
Ast_Type *resolved_type;
|
||||
Ast_Decl *resolved_operator_overload;
|
||||
union{
|
||||
Ast_Type *index_original_type;
|
||||
Ast_Type *cast_after_type;
|
||||
Ast_Type *dot_access_step_resolution;
|
||||
};
|
||||
};
|
||||
|
||||
struct Ast_Atom: Ast_Expr{
|
||||
// We have a field type here
|
||||
// it has a different purpose from the
|
||||
// resolved_type of Ast_Expr, it describes
|
||||
// the inherent type of a value
|
||||
//
|
||||
// resolved_type is a solid type that
|
||||
// can be use during code generation
|
||||
// it cannot be untyped. (or at least thats the hope :)
|
||||
/*#import meta
|
||||
meta.inline_value_fields()
|
||||
*/
|
||||
union {
|
||||
Value value;
|
||||
struct {
|
||||
Ast_Type *type;
|
||||
Ast_Decl *resolved_decl;
|
||||
union {
|
||||
bool bool_val;
|
||||
F64 f64_val;
|
||||
Intern_String intern_val;
|
||||
BigInt big_int_val;
|
||||
Ast_Type *type_val;
|
||||
};
|
||||
};
|
||||
};
|
||||
/*END*/
|
||||
};
|
||||
|
||||
typedef U32 Ast_Call_Item_Flag;
|
||||
enum{
|
||||
CALL_INDEX = bit_flag(1),
|
||||
CALL_NAME = bit_flag(2),
|
||||
CALL_INCLUDED= bit_flag(4),
|
||||
};
|
||||
|
||||
struct Ast_Call_Item: Ast_Expr{
|
||||
Ast_Call_Item_Flag call_flags;
|
||||
S32 resolved_index;
|
||||
Ast_Expr *item;
|
||||
union {
|
||||
Ast_Atom *name;
|
||||
Ast_Expr *index;
|
||||
};
|
||||
Intern_String resolved_name;
|
||||
};
|
||||
|
||||
struct Ast_Lambda;
|
||||
struct Ast_Call: Ast_Expr{
|
||||
union{
|
||||
Ast_Expr *name;
|
||||
Ast_Expr *typespec;
|
||||
};
|
||||
Array<Ast_Call_Item *> exprs;
|
||||
Ast_Decl *resolved_decl;
|
||||
};
|
||||
|
||||
struct Ast_Var_Unpack: Ast_Expr{
|
||||
Array<Ast_Decl *> vars;
|
||||
Ast_Expr *expr;
|
||||
};
|
||||
|
||||
struct Ast_Unary: Ast_Expr{
|
||||
Token_Kind op;
|
||||
Ast_Expr *expr;
|
||||
U64 padding[2]; // For folding constants into atoms
|
||||
};
|
||||
|
||||
struct Ast_Index: Ast_Expr{
|
||||
Ast_Expr *expr;
|
||||
Ast_Expr *index;
|
||||
};
|
||||
|
||||
struct Ast_Binary: Ast_Expr{
|
||||
Token_Kind op;
|
||||
Ast_Expr *left;
|
||||
Ast_Expr *right;
|
||||
Ast_Type *before_type;
|
||||
};
|
||||
|
||||
struct Ast_Builtin: Ast_Expr{
|
||||
Ast_Expr *expr;
|
||||
Intern_String assert_message;
|
||||
U64 padding[1]; // For folding constants into atoms
|
||||
};
|
||||
|
||||
// Problem: We are parsing out of order, in the middle of parsing a function
|
||||
// we can jump down a different function, we cant therfore use global map.
|
||||
// Each scope needs to have it's checked locals list. To lookup syms we need to
|
||||
// look into global scope and to the locals list.
|
||||
//
|
||||
|
||||
struct Ast_Return: Ast{
|
||||
Ast_Type *resolved_type;
|
||||
Array<Ast_Expr *> expr;
|
||||
};
|
||||
|
||||
struct Ast_If_Node: Ast{
|
||||
Ast_Expr *expr ;
|
||||
Ast_Scope *scope;
|
||||
Ast_Binary*init;
|
||||
};
|
||||
|
||||
struct Ast_If: Ast{
|
||||
Array<Ast_If_Node *> ifs;
|
||||
};
|
||||
|
||||
struct Ast_Pass: Ast{};
|
||||
struct Ast_Break: Ast{};
|
||||
|
||||
struct Ast_For: Ast{
|
||||
Ast_Expr *init;
|
||||
Ast_Expr *cond;
|
||||
Ast_Expr *iter;
|
||||
Ast_Scope *scope;
|
||||
|
||||
Ast_Decl *array_traversal_var;
|
||||
bool is_array_traversal;
|
||||
bool is_also_slice_traversal;
|
||||
};
|
||||
|
||||
struct Ast_Lambda : Ast_Expr {
|
||||
Array<Ast_Decl *> args;
|
||||
Array<Ast_Expr *> ret;
|
||||
Ast_Scope *scope;
|
||||
};
|
||||
|
||||
struct Ast_Array: Ast_Expr{
|
||||
Ast_Expr *base;
|
||||
Ast_Expr *expr;
|
||||
U64 padding[2];
|
||||
};
|
||||
|
||||
struct Ast_Switch_Case: Ast{
|
||||
Array<Ast_Expr *> labels;
|
||||
Ast_Scope *scope;
|
||||
B32 fallthrough;
|
||||
};
|
||||
|
||||
struct Ast_Switch: Ast{
|
||||
Ast_Expr *value;
|
||||
Array<Ast_Switch_Case *> cases;
|
||||
Ast_Scope *default_scope;
|
||||
};
|
||||
|
||||
/*
|
||||
How does current declaration order resolver works:
|
||||
* First we put all the global declarations into the global scope (when parsing) all unresolved
|
||||
* All the types are declared INCOMPLETE and RESOLVED
|
||||
* We descent the tree by resolving each of the named declarations, we resolve by their name
|
||||
When we start resolving we set RESOLVING flag and when we complete RESOLVED flag
|
||||
and put into ordered list
|
||||
* When we meet a symbol (named declaration) while descending the tree,
|
||||
we resolve that symbol instead before resolving current declaration.
|
||||
* When we meet a declaration that requires size of a type - field access, var assignment,
|
||||
we need to call "complete_type", it sets COMPLETING flag.
|
||||
This call resolves all the dependencies of that type,
|
||||
sets size of type and marks it as COMPLETE and puts into ordered list.
|
||||
If it detects COMPLETING while
|
||||
resolving, we got a circular dependency. That might happen when we have
|
||||
that struct without pointer inside itself.
|
||||
|
||||
*/
|
||||
|
||||
struct Ast_Scope: Ast{
|
||||
String debug_name; // Dont use
|
||||
List<Ast_Scope *> implicit_imports;
|
||||
List<Ast_Decl *> decls;
|
||||
Array<Ast *> stmts;
|
||||
|
||||
U32 visit_id;
|
||||
U32 scope_id;
|
||||
Ast_Scope *file; // Self referential for file and module
|
||||
Ast_Module *module;
|
||||
};
|
||||
|
||||
enum Ast_Module_State{
|
||||
MODULE_REGISTERED,
|
||||
MODULE_PARSED,
|
||||
MODULE_RESOLVED,
|
||||
};
|
||||
|
||||
struct Ast_Module: Ast_Scope{
|
||||
Ast_Module_State state;
|
||||
String absolute_base_folder;
|
||||
String absolute_file_path;
|
||||
List<Ast_File *> all_loaded_files;
|
||||
};
|
||||
|
||||
struct Ast_File: Ast_Scope{
|
||||
String absolute_base_folder;
|
||||
String absolute_file_path;
|
||||
String filecontent;
|
||||
};
|
||||
|
||||
enum Ast_Decl_State{
|
||||
DECL_NOT_RESOLVED,
|
||||
DECL_RESOLVED,
|
||||
DECL_RESOLVED_TYPE,
|
||||
DECL_RESOLVING,
|
||||
};
|
||||
|
||||
struct Ast_Decl: Ast{
|
||||
Ast_Decl_State state;
|
||||
Intern_String name;
|
||||
Intern_String unique_name; // For code generation, currently only present on lambdas
|
||||
|
||||
U64 operator_overload_arguments_hash;
|
||||
Operator_Info *overload_op_info;
|
||||
|
||||
Ast_Scope *scope;
|
||||
Ast_Expr *typespec;
|
||||
union{
|
||||
Ast_Expr *expr;
|
||||
Ast_Lambda *lambda;
|
||||
};
|
||||
|
||||
/*#import meta
|
||||
meta.inline_value_fields()
|
||||
*/
|
||||
union {
|
||||
Value value;
|
||||
struct {
|
||||
Ast_Type *type;
|
||||
Ast_Decl *resolved_decl;
|
||||
union {
|
||||
bool bool_val;
|
||||
F64 f64_val;
|
||||
Intern_String intern_val;
|
||||
BigInt big_int_val;
|
||||
Ast_Type *type_val;
|
||||
};
|
||||
};
|
||||
};
|
||||
/*END*/
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// AST Constructors beginning with expressions
|
||||
//-----------------------------------------------------------------------------
|
||||
#define AST_NEW(T,ikind,ipos,iflags) \
|
||||
Ast_##T *result = arena_push_type(pctx->perm, Ast_##T, AF_ZeroMemory);\
|
||||
result->flags = iflags; \
|
||||
|
||||
122
core_compiler.h
122
core_compiler.h
@@ -1,127 +1,5 @@
|
||||
struct Ast_Scope;
|
||||
struct Ast_Decl;
|
||||
struct Ast_File_Namespace;
|
||||
struct Ast_File;
|
||||
struct Ast_Module;
|
||||
struct Ast_Type;
|
||||
struct Ast;
|
||||
struct Ast_Expr;
|
||||
|
||||
|
||||
enum Token_Kind{
|
||||
TK_End,
|
||||
|
||||
/*#
|
||||
import meta
|
||||
for i in meta.token_kinds:
|
||||
print(" TK_" + i[0] + ",")
|
||||
*/
|
||||
TK_Mul,
|
||||
TK_Div,
|
||||
TK_Mod,
|
||||
TK_LeftShift,
|
||||
TK_RightShift,
|
||||
TK_FirstMul = TK_Mul,
|
||||
TK_LastMul = TK_RightShift,
|
||||
TK_Add,
|
||||
TK_Sub,
|
||||
TK_FirstAdd = TK_Add,
|
||||
TK_LastAdd = TK_Sub,
|
||||
TK_Equals,
|
||||
TK_LesserThenOrEqual,
|
||||
TK_GreaterThenOrEqual,
|
||||
TK_LesserThen,
|
||||
TK_GreaterThen,
|
||||
TK_NotEquals,
|
||||
TK_FirstCompare = TK_Equals,
|
||||
TK_LastCompare = TK_NotEquals,
|
||||
TK_BitAnd,
|
||||
TK_BitOr,
|
||||
TK_BitXor,
|
||||
TK_And,
|
||||
TK_Or,
|
||||
TK_FirstLogical = TK_BitAnd,
|
||||
TK_LastLogical = TK_Or,
|
||||
TK_Neg,
|
||||
TK_Not,
|
||||
TK_Decrement,
|
||||
TK_Increment,
|
||||
TK_PostDecrement,
|
||||
TK_PostIncrement,
|
||||
TK_Assign,
|
||||
TK_ColonAssign,
|
||||
TK_DivAssign,
|
||||
TK_MulAssign,
|
||||
TK_ModAssign,
|
||||
TK_SubAssign,
|
||||
TK_AddAssign,
|
||||
TK_AndAssign,
|
||||
TK_OrAssign,
|
||||
TK_XorAssign,
|
||||
TK_LeftShiftAssign,
|
||||
TK_RightShiftAssign,
|
||||
TK_FirstAssign = TK_Assign,
|
||||
TK_LastAssign = TK_RightShiftAssign,
|
||||
TK_OpenParen,
|
||||
TK_CloseParen,
|
||||
TK_OpenBrace,
|
||||
TK_CloseBrace,
|
||||
TK_OpenBracket,
|
||||
TK_CloseBracket,
|
||||
TK_Comma,
|
||||
TK_Pound,
|
||||
TK_Question,
|
||||
TK_ThreeDots,
|
||||
TK_Semicolon,
|
||||
TK_Dot,
|
||||
TK_TwoDots,
|
||||
TK_NewLine,
|
||||
TK_Colon,
|
||||
TK_DoubleColon,
|
||||
TK_At,
|
||||
TK_Arrow,
|
||||
TK_ExprSizeof,
|
||||
TK_DocComment,
|
||||
TK_Comment,
|
||||
TK_Identifier,
|
||||
TK_UnicodeLit,
|
||||
TK_StringLit,
|
||||
TK_Error,
|
||||
TK_Float,
|
||||
TK_Integer,
|
||||
TK_Keyword,
|
||||
/*END*/
|
||||
|
||||
TK_Pointer = TK_Mul,
|
||||
TK_Dereference = TK_BitAnd,
|
||||
|
||||
OPEN_SCOPE = 128,
|
||||
CLOSE_SCOPE,
|
||||
SAME_SCOPE,
|
||||
};
|
||||
|
||||
struct Token{
|
||||
Token_Kind kind;
|
||||
U32 di; // debug_id
|
||||
union{
|
||||
String string;
|
||||
struct{U8 *str; S64 len;};
|
||||
};
|
||||
|
||||
union {
|
||||
U32 unicode;
|
||||
BigInt int_val;
|
||||
F64 f64_val;
|
||||
String error_val;
|
||||
Intern_String intern_val;
|
||||
S64 indent;
|
||||
};
|
||||
|
||||
Intern_String file;
|
||||
S32 line;
|
||||
U8 *line_begin;
|
||||
};
|
||||
|
||||
struct Lex_Stream{
|
||||
String stream;
|
||||
S64 iter;
|
||||
|
||||
597
core_compiler_interface.hpp
Normal file
597
core_compiler_interface.hpp
Normal file
@@ -0,0 +1,597 @@
|
||||
#pragma once
|
||||
#include <stdint.h>
|
||||
|
||||
struct Ast;
|
||||
struct Ast_Scope;
|
||||
struct Ast_Decl;
|
||||
struct Ast_File_Namespace;
|
||||
struct Ast_File;
|
||||
struct Ast_Module;
|
||||
struct Ast_Lambda;
|
||||
struct Ast_Type;
|
||||
struct Ast_Expr;
|
||||
|
||||
#ifndef CORE_STRINGS
|
||||
#define CORE_STRINGS
|
||||
struct String{
|
||||
uint8_t *str;
|
||||
int64_t len;
|
||||
};
|
||||
|
||||
union Intern_String{ // Basically just String
|
||||
String s;
|
||||
struct{
|
||||
uint8_t *str;
|
||||
int64_t len;
|
||||
};
|
||||
};
|
||||
#endif
|
||||
|
||||
enum Token_Kind{
|
||||
TK_End,
|
||||
|
||||
/*#
|
||||
import meta
|
||||
for i in meta.token_kinds:
|
||||
print(" TK_" + i[0] + ",")
|
||||
*/
|
||||
TK_Mul,
|
||||
TK_Div,
|
||||
TK_Mod,
|
||||
TK_LeftShift,
|
||||
TK_RightShift,
|
||||
TK_FirstMul = TK_Mul,
|
||||
TK_LastMul = TK_RightShift,
|
||||
TK_Add,
|
||||
TK_Sub,
|
||||
TK_FirstAdd = TK_Add,
|
||||
TK_LastAdd = TK_Sub,
|
||||
TK_Equals,
|
||||
TK_LesserThenOrEqual,
|
||||
TK_GreaterThenOrEqual,
|
||||
TK_LesserThen,
|
||||
TK_GreaterThen,
|
||||
TK_NotEquals,
|
||||
TK_FirstCompare = TK_Equals,
|
||||
TK_LastCompare = TK_NotEquals,
|
||||
TK_BitAnd,
|
||||
TK_BitOr,
|
||||
TK_BitXor,
|
||||
TK_And,
|
||||
TK_Or,
|
||||
TK_FirstLogical = TK_BitAnd,
|
||||
TK_LastLogical = TK_Or,
|
||||
TK_Neg,
|
||||
TK_Not,
|
||||
TK_Decrement,
|
||||
TK_Increment,
|
||||
TK_PostDecrement,
|
||||
TK_PostIncrement,
|
||||
TK_Assign,
|
||||
TK_ColonAssign,
|
||||
TK_DivAssign,
|
||||
TK_MulAssign,
|
||||
TK_ModAssign,
|
||||
TK_SubAssign,
|
||||
TK_AddAssign,
|
||||
TK_AndAssign,
|
||||
TK_OrAssign,
|
||||
TK_XorAssign,
|
||||
TK_LeftShiftAssign,
|
||||
TK_RightShiftAssign,
|
||||
TK_FirstAssign = TK_Assign,
|
||||
TK_LastAssign = TK_RightShiftAssign,
|
||||
TK_OpenParen,
|
||||
TK_CloseParen,
|
||||
TK_OpenBrace,
|
||||
TK_CloseBrace,
|
||||
TK_OpenBracket,
|
||||
TK_CloseBracket,
|
||||
TK_Comma,
|
||||
TK_Pound,
|
||||
TK_Question,
|
||||
TK_ThreeDots,
|
||||
TK_Semicolon,
|
||||
TK_Dot,
|
||||
TK_TwoDots,
|
||||
TK_NewLine,
|
||||
TK_Colon,
|
||||
TK_DoubleColon,
|
||||
TK_At,
|
||||
TK_Arrow,
|
||||
TK_ExprSizeof,
|
||||
TK_DocComment,
|
||||
TK_Comment,
|
||||
TK_Identifier,
|
||||
TK_UnicodeLit,
|
||||
TK_StringLit,
|
||||
TK_Error,
|
||||
TK_Float,
|
||||
TK_Integer,
|
||||
TK_Keyword,
|
||||
/*END*/
|
||||
|
||||
TK_Pointer = TK_Mul,
|
||||
TK_Dereference = TK_BitAnd,
|
||||
|
||||
OPEN_SCOPE = 128,
|
||||
CLOSE_SCOPE,
|
||||
SAME_SCOPE,
|
||||
};
|
||||
|
||||
struct BigInt {
|
||||
unsigned digit_count;
|
||||
bool is_negative;
|
||||
union {
|
||||
uint64_t digit;
|
||||
uint64_t *digits;
|
||||
};
|
||||
};
|
||||
|
||||
struct Token{
|
||||
Token_Kind kind;
|
||||
uint32_t di; // debug_id
|
||||
union{
|
||||
String string;
|
||||
struct{
|
||||
uint8_t *str;
|
||||
int64_t len;
|
||||
};
|
||||
};
|
||||
|
||||
union {
|
||||
uint32_t unicode;
|
||||
BigInt int_val;
|
||||
double f64_val;
|
||||
String error_val;
|
||||
Intern_String intern_val;
|
||||
int64_t indent;
|
||||
};
|
||||
|
||||
Intern_String file;
|
||||
int32_t line;
|
||||
uint8_t *line_begin;
|
||||
};
|
||||
|
||||
enum Ast_Type_Kind{
|
||||
TYPE_NONE,
|
||||
TYPE_S64, // FIRST_NUMERIC
|
||||
TYPE_S32,
|
||||
TYPE_S16,
|
||||
TYPE_S8 ,
|
||||
TYPE_INT,
|
||||
TYPE_CHAR,
|
||||
TYPE_U64,
|
||||
TYPE_U32,
|
||||
TYPE_U16,
|
||||
TYPE_U8 ,
|
||||
TYPE_F32,
|
||||
TYPE_F64,
|
||||
TYPE_POINTER,
|
||||
TYPE_BOOL, // LAST_NUMERIC
|
||||
TYPE_STRING,
|
||||
TYPE_VOID,
|
||||
TYPE_ARRAY,
|
||||
TYPE_LAMBDA,
|
||||
TYPE_STRUCT,
|
||||
TYPE_UNION,
|
||||
TYPE_ENUM,
|
||||
TYPE_TYPE,
|
||||
TYPE_SLICE,
|
||||
TYPE_TUPLE,
|
||||
|
||||
TYPE_COMPLETING,
|
||||
TYPE_INCOMPLETE,
|
||||
TYPE_UNTYPED_BOOL, // FIRST_TYPED_NUMERIC, FIRST_NUMERIC
|
||||
TYPE_UNTYPED_INT,
|
||||
TYPE_UNTYPED_FLOAT, // LAST_TYPED_NUMERIC
|
||||
TYPE_UNTYPED_STRING,
|
||||
|
||||
TYPE_UNTYPED_FIRST = TYPE_UNTYPED_BOOL,
|
||||
TYPE_UNTYPED_LAST = TYPE_UNTYPED_STRING,
|
||||
|
||||
TYPE_UNTYPED_FIRST_NUMERIC = TYPE_UNTYPED_BOOL,
|
||||
TYPE_UNTYPED_LAST_NUMERIC = TYPE_UNTYPED_FLOAT,
|
||||
|
||||
TYPE_FIRST_NUMERIC = TYPE_S64,
|
||||
TYPE_LAST_NUMERIC = TYPE_BOOL,
|
||||
};
|
||||
|
||||
struct Value {
|
||||
/*#import meta
|
||||
print(meta.value_struct_content)
|
||||
*/
|
||||
Ast_Type *type;
|
||||
Ast_Decl *resolved_decl;
|
||||
union {
|
||||
bool bool_val;
|
||||
double f64_val;
|
||||
Intern_String intern_val;
|
||||
BigInt big_int_val;
|
||||
Ast_Type *type_val;
|
||||
};
|
||||
/*END*/
|
||||
};
|
||||
|
||||
struct Ast_Resolved_Member{
|
||||
Intern_String name;
|
||||
int32_t offset;
|
||||
bool visited;
|
||||
/*#import meta
|
||||
meta.inline_value_fields()
|
||||
*/
|
||||
union {
|
||||
Value value;
|
||||
struct {
|
||||
Ast_Type *type;
|
||||
Ast_Decl *resolved_decl;
|
||||
union {
|
||||
bool bool_val;
|
||||
double f64_val;
|
||||
Intern_String intern_val;
|
||||
BigInt big_int_val;
|
||||
Ast_Type *type_val;
|
||||
};
|
||||
};
|
||||
};
|
||||
/*END*/
|
||||
};
|
||||
|
||||
struct Ast_Type{
|
||||
Ast_Type_Kind kind;
|
||||
int32_t size;
|
||||
int32_t align;
|
||||
int32_t is_unsigned;
|
||||
int32_t type_id;
|
||||
int32_t padding;
|
||||
|
||||
Ast *ast;
|
||||
union{
|
||||
Ast_Type *base;
|
||||
struct{
|
||||
Ast_Type *base;
|
||||
int32_t size;
|
||||
// @note: if you have array with size "[32]"
|
||||
// you still want to pass that array into
|
||||
// a function that expects an array of size "[]"
|
||||
// so we want also should check this
|
||||
uint64_t slice_hash;
|
||||
}arr;
|
||||
struct{
|
||||
Array<Ast_Resolved_Member> members;
|
||||
}agg;
|
||||
struct{
|
||||
Ast_Type * ret;
|
||||
Array<Ast_Type *> args;
|
||||
uint64_t hash_without_ret;
|
||||
}func;
|
||||
};
|
||||
};
|
||||
|
||||
enum Ast_Kind: uint32_t{
|
||||
AST_NONE,
|
||||
|
||||
AST_NAMESPACE,
|
||||
|
||||
AST_MODULE,
|
||||
AST_FILE,
|
||||
AST_SCOPE,
|
||||
AST_VALUE,
|
||||
AST_CAST,
|
||||
AST_IDENT,
|
||||
AST_INDEX,
|
||||
AST_UNARY,
|
||||
AST_BINARY,
|
||||
AST_CALL_ITEM,
|
||||
AST_CALL,
|
||||
|
||||
AST_CONSTANT_ASSERT,
|
||||
AST_RUNTIME_ASSERT,
|
||||
AST_SIZE_OF,
|
||||
AST_LENGTH_OF,
|
||||
AST_ALIGN_OF,
|
||||
AST_TYPE_OF,
|
||||
|
||||
AST_SWITCH,
|
||||
AST_SWITCH_CASE,
|
||||
AST_VAR_UNPACK,
|
||||
AST_BREAK,
|
||||
AST_COMPOUND,
|
||||
AST_TYPE,
|
||||
AST_VAR,
|
||||
AST_CONST,
|
||||
AST_POINTER,
|
||||
AST_ARRAY,
|
||||
AST_FOR,
|
||||
AST_IF,
|
||||
AST_IF_NODE,
|
||||
AST_RETURN,
|
||||
AST_BLOCK,
|
||||
AST_PASS,
|
||||
AST_LAMBDA,
|
||||
AST_LAMBDA_EXPR,
|
||||
AST_LAMBDA_ARG,
|
||||
AST_ENUM,
|
||||
AST_ENUM_MEMBER,
|
||||
AST_STRUCT,
|
||||
};
|
||||
|
||||
typedef uint32_t Ast_Flag;
|
||||
enum{
|
||||
AST_EXPR = 1ull << 1,
|
||||
AST_STMT = 1ull << 2,
|
||||
AST_STRICT = 1ull << 3,
|
||||
AST_AGGREGATE = 1ull << 4,
|
||||
AST_AGGREGATE_CHILD = 1ull << 5,
|
||||
AST_ATOM = 1ull << 7,
|
||||
AST_FOREIGN = 1ull << 8,
|
||||
AST_DECL = 1ull << 9,
|
||||
AST_GLOBAL = 1ull << 10,
|
||||
AST_FLAG = 1ull << 11,
|
||||
AST_VAR_IS_CONST = 1ull << 12,
|
||||
AST_OPERATOR_OVERLOAD = 1ull << 13,
|
||||
AST_IS_LVALUE = 1ull << 14,
|
||||
};
|
||||
|
||||
struct Ast{
|
||||
uint64_t di; // Debug id, shouldn't ever be used in the program
|
||||
Token *pos;
|
||||
|
||||
Ast_Kind kind;
|
||||
Ast_Scope *parent_scope;
|
||||
Ast_Flag flags;
|
||||
};
|
||||
|
||||
struct Ast_Expr:Ast{
|
||||
Ast_Type *resolved_type;
|
||||
Ast_Decl *resolved_operator_overload;
|
||||
union{
|
||||
Ast_Type *index_original_type;
|
||||
Ast_Type *cast_after_type;
|
||||
Ast_Type *dot_access_step_resolution;
|
||||
};
|
||||
};
|
||||
|
||||
struct Ast_Atom: Ast_Expr{
|
||||
// We have a field type here
|
||||
// it has a different purpose from the
|
||||
// resolved_type of Ast_Expr, it describes
|
||||
// the inherent type of a value
|
||||
//
|
||||
// resolved_type is a solid type that
|
||||
// can be use during code generation
|
||||
// it cannot be untyped. (or at least thats the hope :)
|
||||
/*#import meta
|
||||
meta.inline_value_fields()
|
||||
*/
|
||||
union {
|
||||
Value value;
|
||||
struct {
|
||||
Ast_Type *type;
|
||||
Ast_Decl *resolved_decl;
|
||||
union {
|
||||
bool bool_val;
|
||||
double f64_val;
|
||||
Intern_String intern_val;
|
||||
BigInt big_int_val;
|
||||
Ast_Type *type_val;
|
||||
};
|
||||
};
|
||||
};
|
||||
/*END*/
|
||||
};
|
||||
|
||||
typedef uint32_t Ast_Call_Item_Flag;
|
||||
enum{
|
||||
CALL_INDEX = 1ull << 1,
|
||||
CALL_NAME = 1ull << 2,
|
||||
CALL_INCLUDED= 1ull << 4,
|
||||
};
|
||||
|
||||
struct Ast_Call_Item: Ast_Expr{
|
||||
Ast_Call_Item_Flag call_flags;
|
||||
int32_t resolved_index;
|
||||
Ast_Expr *item;
|
||||
union {
|
||||
Ast_Atom *name;
|
||||
Ast_Expr *index;
|
||||
};
|
||||
Intern_String resolved_name;
|
||||
};
|
||||
|
||||
struct Ast_Call: Ast_Expr{
|
||||
union{
|
||||
Ast_Expr *name;
|
||||
Ast_Expr *typespec;
|
||||
};
|
||||
Array<Ast_Call_Item *> exprs;
|
||||
Ast_Decl *resolved_decl;
|
||||
};
|
||||
|
||||
struct Ast_Var_Unpack: Ast_Expr{
|
||||
Array<Ast_Decl *> vars;
|
||||
Ast_Expr *expr;
|
||||
};
|
||||
|
||||
struct Ast_Unary: Ast_Expr{
|
||||
Token_Kind op;
|
||||
Ast_Expr *expr;
|
||||
uint64_t padding[2]; // For folding constants into atoms
|
||||
};
|
||||
|
||||
struct Ast_Index: Ast_Expr{
|
||||
Ast_Expr *expr;
|
||||
Ast_Expr *index;
|
||||
};
|
||||
|
||||
struct Ast_Binary: Ast_Expr{
|
||||
Token_Kind op;
|
||||
Ast_Expr *left;
|
||||
Ast_Expr *right;
|
||||
Ast_Type *before_type;
|
||||
};
|
||||
|
||||
struct Ast_Builtin: Ast_Expr{
|
||||
Ast_Expr *expr;
|
||||
Intern_String assert_message;
|
||||
uint64_t padding[1]; // For folding constants into atoms
|
||||
};
|
||||
|
||||
// Problem: We are parsing out of order, in the middle of parsing a function
|
||||
// we can jump down a different function, we cant therfore use global map.
|
||||
// Each scope needs to have it's checked locals list. To lookup syms we need to
|
||||
// look into global scope and to the locals list.
|
||||
//
|
||||
|
||||
struct Ast_Return: Ast{
|
||||
Ast_Type *resolved_type;
|
||||
Array<Ast_Expr *> expr;
|
||||
};
|
||||
|
||||
struct Ast_If_Node: Ast{
|
||||
Ast_Expr *expr ;
|
||||
Ast_Scope *scope;
|
||||
Ast_Binary*init;
|
||||
};
|
||||
|
||||
struct Ast_If: Ast{
|
||||
Array<Ast_If_Node *> ifs;
|
||||
};
|
||||
|
||||
struct Ast_Pass: Ast{};
|
||||
struct Ast_Break: Ast{};
|
||||
|
||||
struct Ast_For: Ast{
|
||||
Ast_Expr *init;
|
||||
Ast_Expr *cond;
|
||||
Ast_Expr *iter;
|
||||
Ast_Scope *scope;
|
||||
|
||||
Ast_Decl *array_traversal_var;
|
||||
bool is_array_traversal;
|
||||
bool is_also_slice_traversal;
|
||||
};
|
||||
|
||||
struct Ast_Lambda : Ast_Expr {
|
||||
Array<Ast_Decl *> args;
|
||||
Array<Ast_Expr *> ret;
|
||||
Ast_Scope *scope;
|
||||
};
|
||||
|
||||
struct Ast_Array: Ast_Expr{
|
||||
Ast_Expr *base;
|
||||
Ast_Expr *expr;
|
||||
uint64_t padding[2];
|
||||
};
|
||||
|
||||
struct Ast_Switch_Case: Ast{
|
||||
Array<Ast_Expr *> labels;
|
||||
Ast_Scope *scope;
|
||||
bool fallthrough;
|
||||
};
|
||||
|
||||
struct Ast_Switch: Ast{
|
||||
Ast_Expr *value;
|
||||
Array<Ast_Switch_Case *> cases;
|
||||
Ast_Scope *default_scope;
|
||||
};
|
||||
|
||||
/*
|
||||
How does current declaration order resolver works:
|
||||
* First we put all the global declarations into the global scope (when parsing) all unresolved
|
||||
* All the types are declared INCOMPLETE and RESOLVED
|
||||
* We descent the tree by resolving each of the named declarations, we resolve by their name
|
||||
When we start resolving we set RESOLVING flag and when we complete RESOLVED flag
|
||||
and put into ordered list
|
||||
* When we meet a symbol (named declaration) while descending the tree,
|
||||
we resolve that symbol instead before resolving current declaration.
|
||||
* When we meet a declaration that requires size of a type - field access, var assignment,
|
||||
we need to call "complete_type", it sets COMPLETING flag.
|
||||
This call resolves all the dependencies of that type,
|
||||
sets size of type and marks it as COMPLETE and puts into ordered list.
|
||||
If it detects COMPLETING while
|
||||
resolving, we got a circular dependency. That might happen when we have
|
||||
that struct without pointer inside itself.
|
||||
|
||||
*/
|
||||
|
||||
struct Ast_Scope: Ast{
|
||||
String debug_name; // Dont use
|
||||
List<Ast_Scope *> implicit_imports;
|
||||
List<Ast_Decl *> decls;
|
||||
Array<Ast *> stmts;
|
||||
|
||||
uint32_t visit_id;
|
||||
uint32_t scope_id;
|
||||
Ast_Scope *file; // Self referential for file and module
|
||||
Ast_Module *module;
|
||||
};
|
||||
|
||||
enum Ast_Module_State{
|
||||
MODULE_REGISTERED,
|
||||
MODULE_PARSED,
|
||||
MODULE_RESOLVED,
|
||||
};
|
||||
|
||||
struct Ast_Module: Ast_Scope{
|
||||
Ast_Module_State state;
|
||||
String absolute_base_folder;
|
||||
String absolute_file_path;
|
||||
List<Ast_File *> all_loaded_files;
|
||||
};
|
||||
|
||||
struct Ast_File: Ast_Scope{
|
||||
String absolute_base_folder;
|
||||
String absolute_file_path;
|
||||
String filecontent;
|
||||
};
|
||||
|
||||
enum Ast_Decl_State{
|
||||
DECL_NOT_RESOLVED,
|
||||
DECL_RESOLVED,
|
||||
DECL_RESOLVED_TYPE,
|
||||
DECL_RESOLVING,
|
||||
};
|
||||
|
||||
struct Ast_Operator_Info{
|
||||
Intern_String op;
|
||||
String name;
|
||||
Token_Kind op_kind;
|
||||
bool valid_binary_expr;
|
||||
bool valid_unary_expr;
|
||||
};
|
||||
|
||||
struct Ast_Decl: Ast{
|
||||
Ast_Decl_State state;
|
||||
Intern_String name;
|
||||
Intern_String unique_name; // For code generation, currently only present on lambdas
|
||||
|
||||
uint64_t operator_overload_arguments_hash;
|
||||
Ast_Operator_Info *overload_op_info;
|
||||
|
||||
Ast_Scope *scope;
|
||||
Ast_Expr *typespec;
|
||||
union{
|
||||
Ast_Expr *expr;
|
||||
Ast_Lambda *lambda;
|
||||
};
|
||||
|
||||
/*#import meta
|
||||
meta.inline_value_fields()
|
||||
*/
|
||||
union {
|
||||
Value value;
|
||||
struct {
|
||||
Ast_Type *type;
|
||||
Ast_Decl *resolved_decl;
|
||||
union {
|
||||
bool bool_val;
|
||||
double f64_val;
|
||||
Intern_String intern_val;
|
||||
BigInt big_int_val;
|
||||
Ast_Type *type_val;
|
||||
};
|
||||
};
|
||||
};
|
||||
/*END*/
|
||||
};
|
||||
@@ -1,11 +1,5 @@
|
||||
|
||||
struct Operator_Info{
|
||||
Intern_String op;
|
||||
String name;
|
||||
Token_Kind op_kind;
|
||||
bool valid_binary_expr;
|
||||
bool valid_unary_expr;
|
||||
};
|
||||
|
||||
|
||||
/*#import meta
|
||||
|
||||
@@ -40,7 +34,7 @@ print(" return 0;\n}")
|
||||
|
||||
|
||||
*/
|
||||
Operator_Info op_info_table[] = {
|
||||
Ast_Operator_Info op_info_table[] = {
|
||||
{{}, "MUL"_s, TK_Mul, 1, 0},
|
||||
{{}, "DIV"_s, TK_Div, 1, 0},
|
||||
{{}, "MOD"_s, TK_Mod, 1, 0},
|
||||
@@ -62,7 +56,7 @@ Operator_Info op_info_table[] = {
|
||||
{{}, "NEG"_s, TK_Neg, 0, 1},
|
||||
{{}, "NOT"_s, TK_Not, 0, 1},
|
||||
};
|
||||
CORE_Static Operator_Info *
|
||||
CORE_Static Ast_Operator_Info *
|
||||
get_operator_info(Token_Kind op){
|
||||
switch(op){
|
||||
case TK_Mul: return op_info_table + 0;
|
||||
@@ -89,7 +83,7 @@ get_operator_info(Token_Kind op){
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
CORE_Static Operator_Info *
|
||||
CORE_Static Ast_Operator_Info *
|
||||
get_operator_info(Intern_String op){
|
||||
if(0){}
|
||||
else if(op_info_table[0].op.str == op.str) return op_info_table + 0;
|
||||
|
||||
@@ -268,6 +268,7 @@ For modules it's a bit different cause they should be distributed as valid.
|
||||
#error Couldnt figure out OS using macros
|
||||
#endif
|
||||
|
||||
#include "core_compiler_interface.hpp"
|
||||
#include "c3_big_int.h"
|
||||
#include "core_compiler.h"
|
||||
#include "core_types.h"
|
||||
|
||||
@@ -864,7 +864,7 @@ parse_decl(B32 is_global){
|
||||
if(!expr->scope){
|
||||
compiler_error(tname, "Operator overload doesn't have body");
|
||||
}
|
||||
Operator_Info *op_info = get_operator_info(tname->intern_val);
|
||||
Ast_Operator_Info *op_info = get_operator_info(tname->intern_val);
|
||||
if(!op_info){
|
||||
compiler_error(tname, "This operator cannot be overloaded");
|
||||
}
|
||||
|
||||
@@ -546,7 +546,7 @@ resolve_name(Ast_Scope *scope, Token *pos, Intern_String name, Search_Flag searc
|
||||
|
||||
CORE_Static Ast_Decl *
|
||||
resolve_operator_overload(Ast_Scope *scope, Ast_Type *left, Ast_Type *right, Token *pos, Token_Kind op, U64 argument_hash){
|
||||
Operator_Info *op_info = get_operator_info(op);
|
||||
Ast_Operator_Info *op_info = get_operator_info(op);
|
||||
if(op_info == 0) return 0;
|
||||
|
||||
// Search for all possible candidates in three scopes
|
||||
|
||||
115
core_types.h
115
core_types.h
@@ -1,49 +1,7 @@
|
||||
//-----------------------------------------------------------------------------
|
||||
// Resolved Types
|
||||
//-----------------------------------------------------------------------------
|
||||
enum Ast_Type_Kind{
|
||||
TYPE_NONE,
|
||||
TYPE_S64, // FIRST_NUMERIC
|
||||
TYPE_S32,
|
||||
TYPE_S16,
|
||||
TYPE_S8 ,
|
||||
TYPE_INT,
|
||||
TYPE_CHAR,
|
||||
TYPE_U64,
|
||||
TYPE_U32,
|
||||
TYPE_U16,
|
||||
TYPE_U8 ,
|
||||
TYPE_F32,
|
||||
TYPE_F64,
|
||||
TYPE_POINTER,
|
||||
TYPE_BOOL, // LAST_NUMERIC
|
||||
TYPE_STRING,
|
||||
TYPE_VOID,
|
||||
TYPE_ARRAY,
|
||||
TYPE_LAMBDA,
|
||||
TYPE_STRUCT,
|
||||
TYPE_UNION,
|
||||
TYPE_ENUM,
|
||||
TYPE_TYPE,
|
||||
TYPE_SLICE,
|
||||
TYPE_TUPLE,
|
||||
|
||||
TYPE_COMPLETING,
|
||||
TYPE_INCOMPLETE,
|
||||
TYPE_UNTYPED_BOOL, // FIRST_TYPED_NUMERIC, FIRST_NUMERIC
|
||||
TYPE_UNTYPED_INT,
|
||||
TYPE_UNTYPED_FLOAT, // LAST_TYPED_NUMERIC
|
||||
TYPE_UNTYPED_STRING,
|
||||
|
||||
TYPE_UNTYPED_FIRST = TYPE_UNTYPED_BOOL,
|
||||
TYPE_UNTYPED_LAST = TYPE_UNTYPED_STRING,
|
||||
|
||||
TYPE_UNTYPED_FIRST_NUMERIC = TYPE_UNTYPED_BOOL,
|
||||
TYPE_UNTYPED_LAST_NUMERIC = TYPE_UNTYPED_FLOAT,
|
||||
|
||||
TYPE_FIRST_NUMERIC = TYPE_S64,
|
||||
TYPE_LAST_NUMERIC = TYPE_BOOL,
|
||||
};
|
||||
|
||||
#define CASE_SINT case TYPE_S8:case TYPE_S16:case TYPE_S32:case TYPE_S64: case TYPE_CHAR: case TYPE_INT
|
||||
#define CASE_UINT case TYPE_U8:case TYPE_U16:case TYPE_U32:case TYPE_U64
|
||||
@@ -53,76 +11,3 @@ enum Ast_Type_Kind{
|
||||
#define CASE_STRING case TYPE_UNTYPED_STRING: case TYPE_STRING: case TYPE_POINTER
|
||||
#define CASE_UNTYPED case TYPE_UNTYPED_INT: case TYPE_UNTYPED_BOOL: case TYPE_UNTYPED_FLOAT: case TYPE_UNTYPED_STRING
|
||||
#define ARRAY_SIZE_SLICE (-1)
|
||||
|
||||
struct Value {
|
||||
/*#import meta
|
||||
print(meta.value_struct_content)
|
||||
*/
|
||||
Ast_Type *type;
|
||||
Ast_Decl *resolved_decl;
|
||||
union {
|
||||
bool bool_val;
|
||||
F64 f64_val;
|
||||
Intern_String intern_val;
|
||||
BigInt big_int_val;
|
||||
Ast_Type *type_val;
|
||||
};
|
||||
/*END*/
|
||||
};
|
||||
|
||||
struct Ast;
|
||||
struct Ast_Type;
|
||||
struct Ast_Resolved_Member{
|
||||
Intern_String name;
|
||||
S32 offset;
|
||||
B32 visited;
|
||||
/*#import meta
|
||||
meta.inline_value_fields()
|
||||
*/
|
||||
union {
|
||||
Value value;
|
||||
struct {
|
||||
Ast_Type *type;
|
||||
Ast_Decl *resolved_decl;
|
||||
union {
|
||||
bool bool_val;
|
||||
F64 f64_val;
|
||||
Intern_String intern_val;
|
||||
BigInt big_int_val;
|
||||
Ast_Type *type_val;
|
||||
};
|
||||
};
|
||||
};
|
||||
/*END*/
|
||||
};
|
||||
|
||||
struct Ast_Type{
|
||||
Ast_Type_Kind kind;
|
||||
S32 size;
|
||||
S32 align;
|
||||
S32 is_unsigned;
|
||||
S32 type_id;
|
||||
S32 padding;
|
||||
|
||||
Ast *ast;
|
||||
union{
|
||||
Ast_Type *base;
|
||||
struct{
|
||||
Ast_Type *base;
|
||||
S32 size;
|
||||
// @note: if you have array with size "[32]"
|
||||
// you still want to pass that array into
|
||||
// a function that expects an array of size "[]"
|
||||
// so we want also should check this
|
||||
U64 slice_hash;
|
||||
}arr;
|
||||
struct{
|
||||
Array<Ast_Resolved_Member> members;
|
||||
}agg;
|
||||
struct{
|
||||
Ast_Type * ret;
|
||||
Array<Ast_Type *> args;
|
||||
U64 hash_without_ret;
|
||||
}func;
|
||||
};
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user