mirror of
https://github.com/BoardWare-Genius/jarvis-models.git
synced 2025-12-13 16:53:24 +00:00
feat: runtime
This commit is contained in:
93
runtime/ast/runtime.py
Normal file
93
runtime/ast/runtime.py
Normal file
@ -0,0 +1,93 @@
|
||||
class Runtime:
|
||||
|
||||
def __init__(self, records={}, parent=None):
|
||||
self.parent = parent
|
||||
self.records = records
|
||||
|
||||
def run(self, ast):
|
||||
if ast["type"] == "Program":
|
||||
return self.program(ast)
|
||||
|
||||
def program(self, ast):
|
||||
return self.block(ast.get("body"))
|
||||
|
||||
def block(self, ast):
|
||||
for statement in ast.get("body"):
|
||||
s = self.switch(statement)
|
||||
if s != None:
|
||||
return s
|
||||
|
||||
def switch(self, ast):
|
||||
t = ast["type"]
|
||||
if t == "VariableDeclaration":
|
||||
self.variable_declaration(ast)
|
||||
if t == "AssignmentExpression":
|
||||
self.assignment_expression(ast)
|
||||
if t == "CallExpression":
|
||||
self.call_function(ast)
|
||||
if t == "ReturnStatement":
|
||||
return self.exec_return(ast)
|
||||
|
||||
def assignment_expression(self, ast):
|
||||
id = ast.get("identifier").get("name")
|
||||
v = ast.get("value")
|
||||
l = self.literal(v)
|
||||
self.records[id] = self.unquote(v)
|
||||
|
||||
def _is_call_function(self, ast):
|
||||
return ast["type"] == "CallExpression"
|
||||
|
||||
def call_function(self,ast):
|
||||
id = ast.get("callee").get("name")
|
||||
args = ast.get("arguments")
|
||||
unquoted_args = []
|
||||
for arg in args:
|
||||
unquoted_args.append(self.unquote(arg))
|
||||
fu = self.records.get(id)
|
||||
return fu(*unquoted_args)
|
||||
|
||||
def unquote(self, ast):
|
||||
if self._is_identifier(ast):
|
||||
return self.records.get(ast.get("name"))
|
||||
if self._is_literal(ast):
|
||||
return self.literal(ast)
|
||||
if self._is_call_function(ast):
|
||||
return self.call_function(ast)
|
||||
|
||||
def variable_declaration(self, ast):
|
||||
id = ast.get("identifier").get("name")
|
||||
v = ast.get("value")
|
||||
if self._is_literal(v):
|
||||
l = self.literal(v)
|
||||
if l != None:
|
||||
self.records[id] = l
|
||||
else:
|
||||
raise Exception("Unknown literal type: " + v.get("type"))
|
||||
if self._is_identifier(v):
|
||||
self.records[id] = self.records.get(v.get("name"))
|
||||
|
||||
def literal(self, ast):
|
||||
if ast.get("type") == "StringLiteral":
|
||||
return ast.get("value")
|
||||
elif ast.get("type") == "NumericLiteral":
|
||||
return int(ast.get("value"))
|
||||
elif ast.get("type") == "FloatLiteral":
|
||||
return float(ast.get("value"))
|
||||
|
||||
def _is_identifier(self, ast):
|
||||
return ast["type"] == "Identifier"
|
||||
|
||||
def _is_literal(self, ast):
|
||||
return ast["type"] in ["NumericLiteral", "StringLiteral", "FloatLiteral"]
|
||||
|
||||
def exec_return(self, ast):
|
||||
v = ast.get("value")
|
||||
if self._is_literal(v):
|
||||
return self.literal(v)
|
||||
if self._is_identifier(v):
|
||||
return self.records.get(v.get("name"))
|
||||
if self._is_call_function(v):
|
||||
return self.call_function(v)
|
||||
|
||||
def debug_print_records(self):
|
||||
print(self.records)
|
||||
Reference in New Issue
Block a user