ref: c9abdb3231c701b9602b9d8c74c2cd03299233a9
dir: /parse/parse.h/
typedef uint32_t unichar; typedef unsigned int uint; typedef long long vlong; typedef unsigned long long uvlong; typedef struct Bitset Bitset; typedef struct Tok Tok; typedef struct Node Node; typedef struct Stab Stab; typedef struct Sym Sym; typedef struct Type Type; typedef struct Cstr Cstr; typedef enum { #define O(op) op, #include "ops.def" #undef O } Op; typedef enum { #define N(nt) nt, #include "nodes.def" #undef N } Ntype; typedef enum { #define L(lt) lt, #include "lits.def" #undef L } Littype; typedef enum { #define Ty(t) t, #include "types.def" #undef Ty } Ty; typedef enum { Dclconst = 1 << 0, Dclextern = 1 << 1, } Dclflags; struct Bitset { int nchunks; uint *chunks; }; struct Tok { int type; int line; char *str; }; struct Stab { Stab *super; char *name; /* Contents of stab. * Types and values are in separate namespaces. */ size_t ntypes; Sym **types; size_t nsyms; Sym **syms; }; /* reused for both decls and types */ struct Sym { int line; Node *name; Type *type; }; struct Type { Ty type; int tid; size_t nsub; /* For fnsub, tusub, sdecls, udecls, edecls. */ Bitset cstrs; /* the type constraints matched on this type */ union { Node *name; /* Tyname: unresolved name */ Type **fnsub; /* Tyfunc: return, args */ Type **tusub; /* Tytuple: element types */ Type *pbase; /* Typtr: pointer target */ Type *sbase; /* Tyslice: slice target */ struct { /* Tyarray: array target and size */ Type *abase; Node *asize; }; char *pname; /* Typaram: name of type parameter */ Node **sdecls; /* Tystruct: decls in struct */ Node **udecls; /* Tyunion: decls in union */ Node **edecls; /* Tyenum: decls in enum */ }; }; struct Cstr { int cid; /* unique id */ /* required members */ size_t nreqmemb; Node **reqmemb; /* required functions */ size_t nreqfn; Node **reqfn; }; struct Node { int line; Ntype type; union { struct { char *name; size_t nuses; Node **uses; size_t nstmts; Node **stmts; Stab *globls; Stab *exports; } file; struct { Op op; Type *type; int isconst; size_t nargs; Node **args; } expr; struct { size_t nparts; char **parts; } name; struct { int islocal; char *name; } use; struct { Littype littype; Type *type; union { uvlong intval; double fltval; unichar chrval; char *strval; int boolval; Node *fnval; Node *arrval; }; } lit; struct { Node *init; Node *cond; Node *step; Node *body; } loopstmt; struct { Node *cond; Node *iftrue; Node *iffalse; } ifstmt; struct { Stab *scope; size_t nstmts; Node **stmts; } block; struct { char *name; } lbl; struct { Sym *sym; Node *init; int flags; } decl; struct { Stab *scope; Node **args; size_t nargs; Node *body; } func; }; }; /* globals */ extern int debug; extern char *filename; extern int ignorenl; extern Tok *curtok; /* the last token we tokenized */ extern int line; /* the last line number we tokenized */ extern Node *file; /* the current file we're compiling */ extern Stab *scope; /* the current scope to insert symbols into */ extern Type **typetab; /* type -> type map used by inference. size maintained by type creation code */ extern Type *littypes[]; /* literal type -> type map */ /* data structures */ Bitset *mkbs(); Bitset *dupbs(Bitset *bs); void delbs(Bitset *bs); void bsput(Bitset *bs, uint elt); void bsdel(Bitset *bs, uint elt); int bshas(Bitset *bs, uint elt); void bsunion(Bitset *a, Bitset *b); void bsintersect(Bitset *a, Bitset *b); void bsdiff(Bitset *a, Bitset *b); /* util functions */ void *zalloc(size_t size); void *xalloc(size_t size); void *zrealloc(void *p, size_t oldsz, size_t size); void *xrealloc(void *p, size_t size); void die(char *msg, ...); void fatal(int line, char *fmt, ...); char *strdupn(char *s, size_t len); void *memdup(void *mem, size_t len); /* parsing etc */ void tokinit(char *file); int yylex(void); int yyparse(void); /* stab creation */ Stab *mkstab(Stab *super); Stab *stput(Sym *decl); Sym *stget(char *name); Sym *mksym(int line, Node *name, Type *ty); /* type creation */ void tyinit(); /* sets up built in types */ Type *mkty(int line, Ty ty); Type *mktyvar(int line); Type *mktyparam(int line, char *name); Type *mktynamed(int line, Node *name); Type *mktyarray(int line, Type *base, Node *sz); Type *mktyslice(int line, Type *base); Type *mktyptr(int line, Type *base); Type *mktyfunc(int line, Node **args, size_t nargs, Type *ret); Type *mktystruct(int line, Node **decls, size_t ndecls); Type *mktyunion(int line, Node **decls, size_t ndecls); Type *mktyenum(int line, Node **decls, size_t ndecls); Cstr *mkcstr(int line, char *name, Node **reqmemb, size_t nreqmemb, Node **reqdecl, size_t nreqdecl); /* type manipulation */ int hascstr(Type *t, Cstr *c); char *tyfmt(char *buf, size_t len, Type *t); char *tystr(Type *t); void tlappend(Type ***tl, int *len, Type *t); /* node creation */ Node *mkfile(char *name); Node *mkuse(int line, char *use, int islocal); Node *mkexpr(int line, Op op, ...); /* NULL terminated */ Node *mkcall(int line, Node *fn, Node **args, size_t nargs); Node *mklit(int line, Littype lt, void *val); Node *mkif(int line, Node *cond, Node *iftrue, Node *iffalse); Node *mkloop(int line, Node *init, Node *cond, Node *incr, Node *body); Node *mkblock(int line, Stab *scope); Node *mkbool(int line, int val); Node *mkint(int line, uint64_t val); Node *mkchar(int line, uint32_t val); Node *mkstr(int line, char *s); Node *mkfloat(int line, double flt); Node *mkfunc(int line, Node **args, size_t nargs, Node *body); Node *mkarray(int line, Node **vals); Node *mkname(int line, char *name); Node *mkdecl(int line, Sym *sym); Node *mklabel(int line, char *lbl); /* node util functions */ Type *decltype(Node *n); void addstmt(Node *file, Node *stmt); void setns(Node *n, char *name); void def(Stab *s, Node *n); void deftype(int line, Stab *s, char *name, Type *t); /* usefiles */ void readuse(Node *use, Stab *into); /* typechecking/inference */ void infer(Node *file); /* debug */ void dump(Node *t, FILE *fd); void dumpsym(Sym *s, FILE *fd); char *opstr(Op o); char *nodestr(Ntype nt); char *litstr(Littype lt); char *tidstr(Ty tid); /* convenience func */ void nlappend(Node ***nl, size_t *len, Node *n); void slappend(Sym ***sl, size_t *len, Sym *s); /* backend functions */ void gen();