#!/usr/bin/env python3 import json import sys tokens = dict() program = './ast.json' if len(sys.argv) > 1: program = sys.argv[1] with open(program, 'r') as json_tokens: tokens = json.loads(json_tokens.read()) def throw(token: dict, message): print("{} on line {} ".format(message, token['line_number'])) if token['variant'] == 'syntax_error': print("\033[4m" + token['value'] + "\033[0m") sys.exit(1) def resolve_variabel(tokens, signifier): for token in tokens: if token['variant'] == "variable_declaration" and token['signifier'] == signifier: return token def parse_expression(variable_list, expression, all_tokens): split_on_space = expression.split(" ") if len(split_on_space) == 1: for param in variable_list: if param['signifier'] == expression: if type(param['expression']) == type(dict()): return param['expression']['expression'] match param['type']: case 'string': return str(param['expression']) case 'number': resolved = list() for part in param['expression'].split(' '): if part.isalpha(): variable = resolve_variabel(all_tokens, part) resolved.append(variable) elif part == '+': resolved.append({"variant": "operator", "type": "addition"}) elif part == '-': resolved.append({"variant": "operator", "type": "subtraction"}) elif part == '*': resolved.append({"variant": "operator", "type": "multiplication"}) elif part == '/': resolved.append({"variant": "operator", "type": "division"}) elif part == '%': resolved.append({"variant": "operator", "type": "modulo"}) elif float(part): resolved.append({"expression": part}) if len(resolved) == 3: lhs = resolved[0]['expression'] operator = resolved[1] rhs = resolved[2]['expression'] match operator['type']: case "addition": return str(float(lhs) + float(rhs)) case "subtraction": return str(float(lhs) - float(rhs)) case "multiplication": return str(float(lhs) * float(rhs)) case "division": return str(float(lhs) / float(rhs)) case "modulo": return str(float(lhs) % float(rhs)) else: return "Unknown" for token in tokens: match token['variant']: case "syntax_error": throw(token, "Syntax error") case "function_call": args = token['params'] function = token['function'] params = function['params'] if len(args) != len(params): print(params) throw(token, "Wrong number of arguments") for index in range(0, len(args)): if args[index]['type'] != params[index]['type']: throw(token, "Type missmatch on arguments") signifier = params[index]['name'] params[index] = args[index] params[index]['signifier'] = signifier for part in function['body']: if part['type'] == "stdout": print(parse_expression(params, part['expression'], tokens), end = '') case _: pass # print(token)