compiler, runtime: Begin Runtime Refactor
Continuous Integration / Grammar Tests (push) Failing after 39s
Continuous Integration / Library Format Tests (push) Successful in 1m46s
Continuous Integration / Library Tests (push) Successful in 4m38s

Ultimately, the goal is to completely separate the compilation from
the runtime to make it possible to have the interpreter/evaluator
be "just another" entity that can perform meaningful work when
given a parsed GP4 program.

Signed-off-by: Will Hawkins <hawkinsw@obs.cr>
This commit is contained in:
Will Hawkins
2026-05-29 08:41:49 -04:00
parent 18461a9215
commit 44e93e4cda
30 changed files with 1264 additions and 854 deletions
+59 -52
View File
@@ -22,14 +22,20 @@ import SwiftTreeSitter
import TreeSitterExtensions
import TreeSitterP4
protocol AnyCompilable {
static func Compile(
node: SwiftTreeSitter.Node, withContext context: CompilerContext
) -> Common.Result<(Any, CompilerContext)>
}
public struct SpecialCompilers {
public struct TransitionStatement {
static func Compile(
node: Node, forState state_identifier: Common.Identifier,
withStatements stmts: [EvaluatableStatement], withContext context: CompilerContext
) -> Result<(ParserState, CompilerContext)> {
withStatements stmts: [P4Statement], withContext context: CompilerContext
) -> Result<ParserState> {
#RequireNodeType<Node, (EvaluatableStatement, CompilerContext)>(
#RequireNodeType<Node, P4Statement>(
node: node, type: "parserTransitionStatement", nice_type_name: "parser transition statement"
)
@@ -58,19 +64,18 @@ public struct SpecialCompilers {
switch next_state {
case (_, .some(let instance)):
return .Ok(
(
ParserStateDirectTransition(
name: state_identifier,
withNextState: instance.dataValue() as! InstantiatedParserState,
withStatements: stmts), context
))
ParserStateDirectTransition(
name: state_identifier,
withNextState: instance.dataValue() as! InstantiatedParserState,
withStatements: stmts,
)
)
case (_, .none):
return .Ok(
(
ParserStateDirectTransition(
name: state_identifier,
withNextStateIdentifier: next_state_id, withStatements: stmts), context
))
ParserStateDirectTransition(
name: state_identifier,
withNextStateIdentifier: next_state_id, withStatements: stmts)
)
}
} else {
@@ -95,12 +100,11 @@ public struct SpecialCompilers {
{
case .Ok(let tse):
.Ok(
(
ParserStateSelectTransition(
name: state_identifier, withTransitionExpression: tse as! SelectExpression,
withStatements: stmts,
), context
))
ParserStateSelectTransition(
name: state_identifier, withTransitionExpression: tse as! SelectExpression,
withStatements: stmts,
)
)
case .Error(let e): .Error(e)
}
}
@@ -109,7 +113,7 @@ public struct SpecialCompilers {
public struct Statements {
static func Compile(
node: Node, withContext context: CompilerContext
) -> Result<([EvaluatableStatement], CompilerContext)> {
) -> Result<[P4Statement]> {
if node.nodeType != "statements" && node.nodeType != "parserStatements" {
return Result.Error(
ErrorWithLocation(
@@ -118,15 +122,15 @@ public struct SpecialCompilers {
var errors: (any Errorable)? = .none
var current_context = context
var parsed_s: [EvaluatableStatement] = Array()
var parsed_s: [P4Statement] = Array()
node.enumerateNamedChildren { node in
switch Statement.Compile(
node: node, withContext: current_context)
{
case .Ok((let parsed_statement, let updated_context)):
current_context = updated_context
case .Ok(let parsed_statement):
parsed_s.append(parsed_statement)
current_context = parsed_statement.effect(context: current_context)
case .Error(let e):
errors =
if let errors = errors {
@@ -141,11 +145,20 @@ public struct SpecialCompilers {
return .Error(errors)
}
return Result.Ok((parsed_s, current_context))
return Result.Ok(parsed_s)
}
static func effect(statements: [P4Statement], context: CompilerContext) -> CompilerContext {
var current = context
for s in statements {
current = s.effect(context: current)
}
return current
}
}
static func Compile(
static func CompileParserBody(
withName name: Common.Identifier, withParameters parameters: ParameterList, node: Node,
withContext context: CompilerContext
) -> Result<(P4Lang.Parser, CompilerContext)> {
@@ -167,9 +180,10 @@ public struct SpecialCompilers {
node: parser_state,
withContext: context.update(newInstances: current_context.instances.enter()))
{
case Result.Ok(let (state, updated_context)):
case Result.Ok(let state):
let statement = state as P4Statement
current_context = statement.effect(context: current_context)
parser.states = parser.states.append(state: state)
current_context = updated_context
case Result.Error(let e): error = e
}
}
@@ -245,43 +259,35 @@ public struct SpecialCompilers {
// Try to parse all top-level declarations.
result?.rootNode?.enumerateNamedChildren { (declaration_node: Node) in
let specific_declaration_node = declaration_node.child(at: 0)!
let declaration_parsers: [CompilableDeclaration.Type] = [
Declaration.self, P4Lang.Parser.self,
let declaration_parsers: [String: CompilableStatement.Type] = [
"declaration": Declaration.self,
"instantiation": Instantiation.self,
]
var found_parser = false
for parser in declaration_parsers {
switch parser.Compile(node: specific_declaration_node, withContext: compilation_context) {
case .Ok(.none): {}()
case .Ok(.some((_, let updated_context))):
found_parser = true
compilation_context = updated_context
break
if let parser = declaration_parsers[declaration_node.nodeType!] {
let r = parser.CompileStatement(node: declaration_node, withContext: compilation_context)
switch r {
case .Ok(let compiled):
compilation_context = compiled.effect(context: compilation_context)
case .Error(let e):
found_parser = true
errors =
if let errors = errors {
errors.append(error: e)
} else {
e
}
break
}
}
// If none of the declaration parsers chose to parse, that's an error, too!
if !found_parser {
let no_parser_error = ErrorWithLocation(
sourceLocation: specific_declaration_node.toSourceLocation(),
withError: "Could not find parser for declaration node"
)
}
} else {
let e = ErrorWithLocation(
sourceLocation: declaration_node.toSourceLocation(),
withError:
"\(declaration_node.nodeType!) cannot be at a P4 program top level")
errors =
if let errors = errors {
errors.append(error: no_parser_error)
errors.append(error: e)
} else {
no_parser_error
e
}
}
}
@@ -313,4 +319,5 @@ public struct SpecialCompilers {
return Result.Ok(program)
}
}
}