// SPDX-FileCopyrightText: 2024 Himbeer // // SPDX-License-Identifier: GPL-3.0-or-later package main import ( "io" ) type expression interface { markExpr() line() int } type rootExpr struct { toplevels []expression ln int } func (r *rootExpr) markExpr() {} func (r *rootExpr) line() int { return r.ln } type linkage int const ( defaultLinkage linkage = iota exportLinkage ) func (l linkage) String() string { switch l { case exportLinkage: return "export" } return "" } type functionExpr struct { link linkage name string params *paramExpr returnType string blk *blockExpr ln int } func (f *functionExpr) markExpr() {} func (f *functionExpr) line() int { return f.ln } type paramExpr struct { name string typ string next *paramExpr ln int } func (p *paramExpr) markExpr() {} func (p *paramExpr) line() int { return p.ln } type externFuncExpr struct { name string params *signatureExpr returnType string ln int } func (e *externFuncExpr) markExpr() {} func (e *externFuncExpr) line() int { return e.ln } type signatureExpr struct { typ string next *signatureExpr ln int } func (s *signatureExpr) markExpr() {} func (s *signatureExpr) line() int { return s.ln } type blockExpr struct { stmts []statementExpr ln int } func (b *blockExpr) markExpr() {} func (b *blockExpr) line() int { return b.ln } type statementExpr interface { expression markStmt() } type returnStmt struct { value exprExpr ln int } func (r *returnStmt) markExpr() {} func (r *returnStmt) markStmt() {} func (r *returnStmt) line() int { return r.ln } type declStmt interface { statementExpr markDecl() } type constStmt struct { name string initial exprExpr ln int } func (c *constStmt) markExpr() {} func (c *constStmt) markStmt() {} func (c *constStmt) markDecl() {} func (c *constStmt) line() int { return c.ln } type mutStmt struct { name string initial exprExpr ln int } func (m *mutStmt) markExpr() {} func (m *mutStmt) markStmt() {} func (m *mutStmt) markDecl() {} func (m *mutStmt) line() int { return m.ln } type assignmentStmt interface { statementExpr markAssign() } type assignStmt struct { name string value exprExpr ln int } func (a *assignStmt) markExpr() {} func (a *assignStmt) markStmt() {} func (a *assignStmt) markAssign() {} func (a *assignStmt) line() int { return a.ln } type addAssignStmt struct { name string value exprExpr ln int } func (a *addAssignStmt) markExpr() {} func (a *addAssignStmt) markStmt() {} func (a *addAssignStmt) markAssign() {} func (a *addAssignStmt) line() int { return a.ln } type subAssignStmt struct { name string value exprExpr ln int } func (s *subAssignStmt) markExpr() {} func (s *subAssignStmt) markStmt() {} func (s *subAssignStmt) markAssign() {} func (s *subAssignStmt) line() int { return s.ln } type mulAssignStmt struct { name string value exprExpr ln int } func (m *mulAssignStmt) markExpr() {} func (m *mulAssignStmt) markStmt() {} func (m *mulAssignStmt) markAssign() {} func (m *mulAssignStmt) line() int { return m.ln } type divAssignStmt struct { name string value exprExpr ln int } func (d *divAssignStmt) markExpr() {} func (d *divAssignStmt) markStmt() {} func (d *divAssignStmt) markAssign() {} func (d *divAssignStmt) line() int { return d.ln } type remAssignStmt struct { name string value exprExpr ln int } func (r *remAssignStmt) markExpr() {} func (r *remAssignStmt) markStmt() {} func (r *remAssignStmt) markAssign() {} func (r *remAssignStmt) line() int { return r.ln } type exprExpr interface { expression markExprExpr() cerType() cerType generate(io.Writer) (string, error) } type equalityExpr struct { lhs *comparisonExpr rhs []*equalityRhs ln int } func (e *equalityExpr) markExpr() {} func (e *equalityExpr) markExprExpr() {} func (e *equalityExpr) line() int { return e.ln } func (e *equalityExpr) cerType() cerType { return e.lhs.cerType() } type equalityRhs struct { op equalityOp value *comparisonExpr } type comparisonExpr struct { lhs *termExpr rhs *comparisonRhs ln int } func (c *comparisonExpr) markExpr() {} func (c *comparisonExpr) markExprExpr() {} func (c *comparisonExpr) line() int { return c.ln } func (c *comparisonExpr) cerType() cerType { return c.lhs.cerType() } type comparisonRhs struct { op comparisonOp value *termExpr } type termExpr struct { lhs *numeralExpr rhs []*termRhs ln int } func (t *termExpr) markExpr() {} func (t *termExpr) markExprExpr() {} func (t *termExpr) line() int { return t.ln } func (t *termExpr) cerType() cerType { return t.lhs.cerType() } type termRhs struct { op shiftOp value *numeralExpr } type numeralExpr struct { lhs *factorExpr rhs []*numeralRhs ln int } func (n *numeralExpr) markExpr() {} func (n *numeralExpr) markExprExpr() {} func (n *numeralExpr) line() int { return n.ln } func (n *numeralExpr) cerType() cerType { return n.lhs.cerType() } type numeralRhs struct { op addSubOp value *factorExpr } type factorExpr struct { lhs *unaryExpr rhs []*factorRhs ln int } func (f *factorExpr) markExpr() {} func (f *factorExpr) markExprExpr() {} func (f *factorExpr) line() int { return f.ln } func (f *factorExpr) cerType() cerType { return f.lhs.cerType() } type factorRhs struct { op mulDivOp value *unaryExpr } type unaryExpr struct { op unaryOp value primaryExpr ln int } func (u *unaryExpr) markExpr() {} func (u *unaryExpr) markExprExpr() {} func (u *unaryExpr) line() int { return u.ln } func (u *unaryExpr) cerType() cerType { return u.value.cerType() } type primaryExpr interface { exprExpr markPrimaryExpr() } type literalExpr interface { primaryExpr markLiteralExpr() } type stringExpr struct { segments []string ln int } func (s *stringExpr) markExpr() {} func (s *stringExpr) markExprExpr() {} func (s *stringExpr) markPrimaryExpr() {} func (s *stringExpr) markLiteralExpr() {} func (s *stringExpr) line() int { return s.ln } func (s *stringExpr) cerType() cerType { return nil } // TODO: string type type numberExpr struct { typ string s string ln int } func (n *numberExpr) markExpr() {} func (n *numberExpr) markExprExpr() {} func (n *numberExpr) markPrimaryExpr() {} func (n *numberExpr) markLiteralExpr() {} func (n *numberExpr) line() int { return n.ln } func (n *numberExpr) cerType() cerType { return resolveType(n.typ) } type groupingExpr struct { inner exprExpr ln int } func (g *groupingExpr) markExpr() {} func (g *groupingExpr) markExprExpr() {} func (g *groupingExpr) markPrimaryExpr() {} func (g *groupingExpr) line() int { return g.ln } func (g *groupingExpr) cerType() cerType { return g.inner.cerType() } type callExpr struct { funcName string args *argument numArgs int ln int } func (c *callExpr) markExpr() {} func (c *callExpr) markExprExpr() {} func (c *callExpr) markPrimaryExpr() {} func (c *callExpr) line() int { return c.ln } func (c *callExpr) cerType() cerType { ok, _ := isDeclared(c.funcName, true) if !ok { return nil } return funcs[c.funcName].returnType } type argument struct { value exprExpr next *argument } type varExpr struct { name string ln int } func (v *varExpr) markExpr() {} func (v *varExpr) markExprExpr() {} func (v *varExpr) markPrimaryExpr() {} func (v *varExpr) line() int { return v.ln } func (v *varExpr) cerType() cerType { ok, mutable := isDeclared(v.name, false) if !ok { return nil } if mutable { return localMuts[currentFunc][v.name].typ } return localConsts[currentFunc][v.name].typ }