1
Files
lecture-interpreters/primitives.py
2021-08-09 16:32:53 +02:00

48 lines
1.4 KiB
Python

registry = {}
all_primitives = []
primitive_number_of_arguments = []
def primitive(name, unwrap_spec, wrap_spec):
assert '$' + name not in registry, '${name} already defined'.format(name=name)
primitive_number_of_arguments.append(len(unwrap_spec) - 1) # first argument is the receiver
def expose(func):
def unwrapper(w_receiver, args_w, space):
args = [w_receiver] + args_w
if len(args) != len(unwrap_spec):
raise TypeError(
"Expected {ex} arguments, received {re}.".format(ex=len(unwrap_spec), re=len(args)))
unwrapped_args = ()
for t, arg in zip(unwrap_spec, args):
if t is int:
unwrapped_args += (arg.value, )
else:
unwrapped_args += (arg, )
result = func(*unwrapped_args)
if wrap_spec is int:
return space.newint(result)
return result
unwrapper.__qualname__ = name
all_primitives.append(unwrapper)
registry['$' + name] = len(all_primitives) - 1
return None
return expose
def get_index_of_primitive_named(name):
return registry[name]
def get_number_of_arguments_of_primitive(idx):
return primitive_number_of_arguments[idx]
@primitive('int_add', [int, int], int)
def simple_int_add(a, b):
return a + b
@primitive('int_eq', [int, int], int)
def simple_int_eq(a, b):
return a == b