def main(): import gonelex import goneparse import gonecheck import gonecode import goneblock import sys import ctypes from errors import subscribe_errors, errors_reported from llvm.ee import ExecutionEngine # Load the Gone runtime library (see Makefile) ctypes._dlopen('./gonert.so', ctypes.RTLD_GLOBAL) lexer = gonelex.make_lexer() parser = goneparse.make_parser() with subscribe_errors(lambda msg: sys.stdout.write(msg+"\n")): program = parser.parse(open(sys.argv[1]).read()) # Check the program gonecheck.check_program(program) # If no errors occurred, generate code if not errors_reported(): functions = gonecode.generate_code(program) # Emit the code sequence bv = LLVMBlockVisitor() bv.generate_llvm(functions) print(bv.llvm.module) # Verify and run function that was created during code generation print(":::: RUNNING ::::") bv.llvm.function.verify() llvm_executor = ExecutionEngine.new(bv.llvm.module) llvm_executor.run_function(bv.llvm.vars['__start'], [])
def test_issue100(self): m = Module.new('a') pm = FunctionPassManager.new(m) ee = ExecutionEngine.new(m) pm.add(ee.target_data) ti = Type.int() tf = Type.function(ti, []) f = m.add_function(tf, "func1") bb = f.append_basic_block('entry') b = Builder.new(bb) b.ret(Constant.int(ti, 0)) f.verify() pm.run(f) assert ee.run_function(f, []).as_int() == 0
def __init__(self): self.module = Module.new('generator') # Create a main function with no arguments and add it to the module self.main = self.module.add_function(Type.function(Type.double(), []), "main") # Create a new builder with a single basic block self.builder = Builder.new(self.main.append_basic_block("entry")) # Create an executor engine for JIT and Interpreter execution self.executor = ExecutionEngine.new(self.module)
def bitey_reconstruct(md, bitcode): name, = md mod = new_module(name) llvm_module = Module.from_bitcode(BytesIO(bitcode)) engine = ExecutionEngine.new(llvm_module) make_all_wrappers(llvm_module, engine, mod) return mod
def test_jit_ctypes(self): # This example demonstrates calling an LLVM defined function using # ctypes. It illustrates the common C pattern of having an output # variable in the argument list to the function. The function also # returns an error code upon exit. # setup llvm types ty_errcode = Type.int() ty_float = Type.float() ty_ptr_float = Type.pointer(Type.float()) ty_func = Type.function(ty_errcode, [ty_float, ty_float, ty_ptr_float]) # setup ctypes types ct_errcode = ctypes.c_int ct_float = ctypes.c_float ct_ptr_float = ctypes.POINTER(ct_float) ct_argtypes = [ct_float, ct_float, ct_ptr_float] # generate the function using LLVM my_module = Module.new('my_module') mult = my_module.add_function(ty_func, "mult") mult.args[0].name = "a" mult.args[1].name = "b" mult.args[2].name = "out" # add nocapture to output arg mult.args[2].add_attribute(llvm.core.ATTR_NO_CAPTURE) mult.does_not_throw = True # add nounwind attribute to function bb = mult.append_basic_block("entry") builder = Builder.new(bb) tmp = builder.fmul(mult.args[0], mult.args[1]) builder.store(tmp, mult.args[2]) builder.ret(llvm.core.Constant.int(ty_errcode, 0)) # print the created module logging.debug(my_module) # compile the function ee = ExecutionEngine.new(my_module) # let ctypes know about the function func_ptr_int = ee.get_pointer_to_function(mult) FUNC_TYPE = ctypes.CFUNCTYPE(ct_errcode, *ct_argtypes) py_mult = FUNC_TYPE(func_ptr_int) # now run the function, calling via ctypes output_value = ct_float(123456.0) errcode = py_mult(2.0, 3.0, ctypes.byref(output_value)) self.assertEqual(errcode, 0, msg='unexpected error') self.assertEqual(output_value.value, 6.0)
def test_jit_ctypes(self): # This example demonstrates calling an LLVM defined function using # ctypes. It illustrates the common C pattern of having an output # variable in the argument list to the function. The function also # returns an error code upon exit. # setup llvm types ty_errcode = Type.int() ty_float = Type.float() ty_ptr_float = Type.pointer(Type.float()) ty_func = Type.function(ty_errcode, [ty_float, ty_float, ty_ptr_float]) # setup ctypes types ct_errcode = ctypes.c_int ct_float = ctypes.c_float ct_ptr_float = ctypes.POINTER(ct_float) ct_argtypes = [ct_float, ct_float, ct_ptr_float] # generate the function using LLVM my_module = Module.new('my_module') mult = my_module.add_function(ty_func, "mult") mult.args[0].name = "a" mult.args[1].name = "b" mult.args[2].name = "out" # add nocapture to output arg mult.args[2].add_attribute(llvm.core.ATTR_NO_CAPTURE) mult.does_not_throw = True # add nounwind attribute to function bb = mult.append_basic_block("entry") builder = Builder.new(bb) tmp = builder.fmul( mult.args[0], mult.args[1] ) builder.store( tmp, mult.args[2] ) builder.ret(llvm.core.Constant.int(ty_errcode, 0)) # print the created module logging.debug(my_module) # compile the function ee = ExecutionEngine.new(my_module) # let ctypes know about the function func_ptr_int = ee.get_pointer_to_function( mult ) FUNC_TYPE = ctypes.CFUNCTYPE(ct_errcode, *ct_argtypes) py_mult = FUNC_TYPE(func_ptr_int) # now run the function, calling via ctypes output_value = ct_float(123456.0) errcode = py_mult( 2.0, 3.0, ctypes.byref(output_value) ) self.assertEqual(errcode, 0, msg='unexpected error') self.assertEqual(output_value.value, 6.0)
def debug_ctypes(mod, spine, constructors, rettype=None): from bitey.bind import map_llvm_to_ctypes from imp import new_module engine = ExecutionEngine.new(mod) py = new_module('') if not rettype: map_llvm_to_ctypes(spine, py) rettype = py.maybe else: rettype = rettype return [wrap_constructor(c, engine, py, rettype) for c in constructors]
def main(): import gonelex import goneparse import gonecheck import gonecode import sys import ctypes import time import argparse from errors import subscribe_errors, errors_reported from llvm.ee import ExecutionEngine global args parser = argparse.ArgumentParser("Compile and run a Gone program from a .g file") parser.add_argument('file', type=str, default='', nargs=1, help="the file containing Gone source") parser.add_argument('--verbose', '-v', action="store_true", help="print verbose output") parser.add_argument('--validate', '-c', action="store_true", help="perform llvm bitcode validation prior to program execution") args = parser.parse_args() # Load the Gone runtime library (see Makefile) ctypes._dlopen('./gonert.so', ctypes.RTLD_GLOBAL) lexer = gonelex.make_lexer() parser = goneparse.make_parser() with subscribe_errors(lambda msg: sys.stdout.write(msg + "\n")): program = parser.parse(open(args.file[0]).read()) gonecheck.check_program(program) if not errors_reported(): code = gonecode.generate_code(program) g = GenerateLLVMBlockVisitor() g.visit_functions(code.functions) if args.verbose: print("---- NATIVE ASSEMBLY ----") print(g.generator.module.to_native_assembly()) print("---- END NATIVE ASSEMBLY ----") if args.verbose: print(":::: RUNNING ::::") start = time.time() llvm_executor = ExecutionEngine.new(g.generator.module) llvm_executor.run_function(g.generator.main_func, []) if args.verbose: print(":::: FINISHED ::::") print("execution time: {0:.15f}s".format(time.time() - start))
def init_llvm(self): mod = Module.new("exprllvm") self.engine = ExecutionEngine.new(mod) # functions self.llvm_functions = {} func = Function.new(mod, Type.function( Type.void(), [], False), "main") self.llvm_functions['main'] = func block = func.append_basic_block("entry") # builder builder = Builder.new(block) self.builder = builder # add some pre-defined functions print_int = Function.new(mod, Type.function( Type.void(), [Type.int()], False), "print_int") self.llvm_functions['print_int'] = print_int self.builder.call(print_int, [Constant.int(Type.int(),3)]) self.builder.ret_void()
from llvm.ee import ExecutionEngine, TargetData from llvm.passes import FunctionPassManager import llvm.core from llvm.core import FCMP_ULT, FCMP_ONE, ICMP_NE, CC_FASTCALL, CC_C from llvm.passes import (PASS_PROMOTE_MEMORY_TO_REGISTER, PASS_INSTRUCTION_COMBINING, PASS_REASSOCIATE, PASS_GVN, PASS_CFG_SIMPLIFICATION) G_LLVM_MODULE = Module.new('my cool jit') G_LLVM_BUILDER = None G_NAMED_VALUES = {} G_LLVM_PASS_MANAGER = FunctionPassManager.new(G_LLVM_MODULE) G_LLVM_EXECUTOR = ExecutionEngine.new(G_LLVM_MODULE) G_BINOP_PRECEDENCE = {} llvm.core.load_library_permanently('/home/popolit/code/ibcl/putchard.so') llvm.core.load_library_permanently('/home/popolit/code/ibcl/intern.so') llvm.core.load_library_permanently('/home/popolit/code/ibcl/repr.so') llvm.core.load_library_permanently('/home/popolit/code/ibcl/eq.so') llvm.core.load_library_permanently('/home/popolit/code/ibcl/cons.so') llvm.core.load_library_permanently('/home/popolit/code/ibcl/atom.so') llvm.core.load_library_permanently('/home/popolit/code/ibcl/carcdr.so') llvm.core.load_library_permanently('/home/popolit/code/ibcl/read.so') llvm.core.load_library_permanently('/home/popolit/code/ibcl/length.so') llvm.core.load_library_permanently( '/home/popolit/code/ibcl/find_llvm_function.so') def create_entry_block_alloca(function, var_name):
return_value = self.body.gen_code(module, builder, variables) builder.ret(return_value) function.verify() return function test = """ def fib(n) if n < 3 then 1 else fib(n-1) + fib(n-2) def div(a b) a/b fib(40) """ module = Module.new('sfpl') from pprint import * res = program.parseString(test, parseAll=True) pprint(res.asList()) funs = [x.gen_code(module, None, None) for x in res[:-1]] fun = FunctionDef('', [], res[-1]).gen_code(module, None, None) from llvm.ee import ExecutionEngine, TargetData g_llvm_executor = ExecutionEngine.new(module) ret = g_llvm_executor.run_function(fun, []) print ret.as_real(Type.double())
func = functype(addr) func # Call the resulting function func(2) func(0) from llvm.core import Module, Function, Type, Builder mod = Module.new('example') f = Function.new(mod,Type.function(Type.double(), block = f.append_basic_block('entry') builder = Builder.new(block) x2 = builder.fmul(f.args[0],f.args[0]) y2 = builder.fmul(f.args[1],f.args[1]) r = builder.fadd(x2,y2) builder.ret(r) from llvm.ee import ExecutionEngine engine = ExecutionEngine.new(mod) ptr = engine.get_pointer_to_function(f) ptr foo = ctypes.CFUNCTYPE(ctypes.c_double, ctypes.c_double, ctypes.c_double)(ptr) # Call the resulting function foo(2,3) foo(4,5) foo(1,2)
def run( py_main_func, *call_args ): from rpy.rtypes import ConstantTypeRegistry registry = ConstantTypeRegistry() # Annotates call graph types (local var, functions param/return...) print( '\nAnalysing call graph...\n%s' % ('='*70) ) annotator = CallableGraphAnnotator( registry ) annotator.set_entry_point( py_main_func, call_args ) annotator.annotate_dependencies() # Generate LLVM code from rpy.codegenerator import ModuleGenerator, FunctionCodeGenerator, L_INT_TYPE, L_BOOL_TYPE module = ModuleGenerator( registry ) l_func_entry, l_func_type = None, None # Declares all function in modules fn_code_generators = [] for r_func_type, type_annotator in annotator.annotator_by_callable.items(): py_func = r_func_type.get_function_object() print( '\nDeclaring function:\n%s\nPython: %s\nRType: %s' % ('-'*70, py_func, r_func_type) ) func_generator = FunctionCodeGenerator( py_func, module, annotator ) fn_code_generators.append( (r_func_type, func_generator) ) # Makes sure that all class type have their struct/attribute index dict initialized for r_func_type, _ in fn_code_generators: if r_func_type.is_constructor(): module.llvm_type_from_rtype( r_func_type ) # Generates function's code, possibly referencing previously declared functions for r_func_type, func_generator in fn_code_generators: print( '\nGenerating code for function:\n%s\n%s\nSouce:\n' % ('-'*70, r_func_type) ) print( func_generator.annotation.get_function_source() ) func_generator.generate_llvm_code() func_generator.report() if r_func_type.get_function_object() is py_main_func: l_func_entry = func_generator.l_func l_func_type = func_generator.l_func_type print( 'Generated module code:' ) print( '----------------------\n%s', module.l_module ) optimize( module ) print( 'Generated module code after optimization:' ) print( '-----------------------------------------\n', module.l_module ) # Execute generate code # 1) Convert call args into generic value print( 'Invoking function with %r' % (call_args,) ) from llvm.core import ModuleProvider, TYPE_VOID from llvm.ee import ExecutionEngine, GenericValue module_provider = ModuleProvider.new( module.l_module ) engine = ExecutionEngine.new( module_provider ) l_call_args = [] for py_call_arg, l_arg in zip( call_args, l_func_entry.args ): if l_arg.type == L_INT_TYPE: l_call_args.append( GenericValue.int_signed( L_INT_TYPE, py_call_arg ) ) elif l_arg.type == L_BOOL_TYPE: l_call_args.append( GenericValue.int( L_BOOL_TYPE, py_call_arg ) ) else: raise ValueError( 'Unsupported parameter "%s" of type: %r' % (py_call_arg, l_arg_type) ) # 2) run the functions l_return_value = engine.run_function( l_func_entry, l_call_args ) # 3) convert LLVM return value into python type if l_func_type.return_type == L_INT_TYPE: return l_return_value.as_int_signed() elif l_func_type.return_type == L_BOOL_TYPE: return l_return_value.as_int() and True or False elif l_func_type.return_type.kind == TYPE_VOID: return None print( 'Return:', l_return_value ) raise ValueError( 'Unsupported return type "%s"' % l_func_entry.return_type )
import cmexception from lexer import LexmeType g_llvm_module = Module.new('CMCompiler') g_llvm_builder = None func_table = {} constant_string_num = 0 g_llvm_pass_manager = FunctionPassManager.new(g_llvm_module) g_llvm_pass_manager.add(PASS_INSTCOMBINE) g_llvm_pass_manager.add(PASS_REASSOCIATE) g_llvm_pass_manager.add(PASS_GVN) g_llvm_pass_manager.add(PASS_SIMPLIFYCFG) g_llvm_pass_manager.initialize() g_llvm_executor = ExecutionEngine.new(g_llvm_module) #Base class of each Abstract Syntax Tree Node class ASTNode: def __init__(self, context): self.context = context def print_ast(self): pass #each node can implements this method to generate LLVMIR code def code_gen(self): pass
l_point_struct_type = lcore.Type.struct( l_attribute_types ) module = lcore.Module.new('structdemo') type_main = Type.function(Type.void(), []) fn_main = module.add_function( type_main, 'test_main' ) basic_block = fn_main.append_basic_block("entry") builder = lcore.Builder.new(basic_block) # Allocates the structure on the stack l_point = builder.alloca( l_point_struct_type, 'point_var' ) constant_0 = lcore.Constant.int( ty_i32, 0 ) constant_point_x_index = lcore.Constant.int( ty_i32, 0 ) constant_point_y_index = lcore.Constant.int( ty_i32, 1 ) constant_16 = lcore.Constant.int( ty_i32, 16 ) l_px = builder.gep( l_point, [constant_0, constant_point_x_index] ) # gep = getelementptr l_py = builder.gep( l_point, [constant_0, constant_point_y_index] ) # gep = getelementptr builder.store( constant_16, l_px ) builder.store( constant_16, l_py ) builder.ret_void() print( module ) from llvm.ee import ExecutionEngine, GenericValue module_provider = lcore.ModuleProvider.new( module ) engine = ExecutionEngine.new( module_provider ) engine.run_function( fn_main, [] )
def run(py_main_func, *call_args): from rpy.rtypes import ConstantTypeRegistry registry = ConstantTypeRegistry() # Annotates call graph types (local var, functions param/return...) print('\nAnalysing call graph...\n%s' % ('=' * 70)) annotator = CallableGraphAnnotator(registry) annotator.set_entry_point(py_main_func, call_args) annotator.annotate_dependencies() # Generate LLVM code from rpy.codegenerator import ModuleGenerator, FunctionCodeGenerator, L_INT_TYPE, L_BOOL_TYPE module = ModuleGenerator(registry) l_func_entry, l_func_type = None, None # Declares all function in modules fn_code_generators = [] for r_func_type, type_annotator in annotator.annotator_by_callable.items(): py_func = r_func_type.get_function_object() print('\nDeclaring function:\n%s\nPython: %s\nRType: %s' % ('-' * 70, py_func, r_func_type)) func_generator = FunctionCodeGenerator(py_func, module, annotator) fn_code_generators.append((r_func_type, func_generator)) # Makes sure that all class type have their struct/attribute index dict initialized for r_func_type, _ in fn_code_generators: if r_func_type.is_constructor(): module.llvm_type_from_rtype(r_func_type) # Generates function's code, possibly referencing previously declared functions for r_func_type, func_generator in fn_code_generators: print('\nGenerating code for function:\n%s\n%s\nSouce:\n' % ('-' * 70, r_func_type)) print(func_generator.annotation.get_function_source()) func_generator.generate_llvm_code() func_generator.report() if r_func_type.get_function_object() is py_main_func: l_func_entry = func_generator.l_func l_func_type = func_generator.l_func_type print('Generated module code:') print('----------------------\n%s', module.l_module) optimize(module) print('Generated module code after optimization:') print('-----------------------------------------\n', module.l_module) # Execute generate code # 1) Convert call args into generic value print('Invoking function with %r' % (call_args, )) from llvm.core import ModuleProvider, TYPE_VOID from llvm.ee import ExecutionEngine, GenericValue module_provider = ModuleProvider.new(module.l_module) engine = ExecutionEngine.new(module_provider) l_call_args = [] for py_call_arg, l_arg in zip(call_args, l_func_entry.args): if l_arg.type == L_INT_TYPE: l_call_args.append(GenericValue.int_signed(L_INT_TYPE, py_call_arg)) elif l_arg.type == L_BOOL_TYPE: l_call_args.append(GenericValue.int(L_BOOL_TYPE, py_call_arg)) else: raise ValueError('Unsupported parameter "%s" of type: %r' % (py_call_arg, l_arg_type)) # 2) run the functions l_return_value = engine.run_function(l_func_entry, l_call_args) # 3) convert LLVM return value into python type if l_func_type.return_type == L_INT_TYPE: return l_return_value.as_int_signed() elif l_func_type.return_type == L_BOOL_TYPE: return l_return_value.as_int() and True or False elif l_func_type.return_type.kind == TYPE_VOID: return None print('Return:', l_return_value) raise ValueError('Unsupported return type "%s"' % l_func_entry.return_type)
from llvm.core import Module, Builder, Function, Type, Constant, GlobalVariable from llvm.ee import ExecutionEngine, GenericValue import ctypes mod = Module.new("hello") hello_func = Function.new(mod, Type.function(Type.int(), [], False), "hello") block = hello_func.append_basic_block('entry') builder = Builder.new(block) builder.ret(Constant.int(Type.int(), 69)) #print(mod) engine = ExecutionEngine.new(mod) result = engine.run_function(hello_func, []) #print(result.as_int()) dsquared_func = Function.new(mod, Type.function(Type.double(), [Type.double(), Type.double()], False), "dsquared") block = dsquared_func.append_basic_block("entry") builder = Builder.new(block) x = dsquared_func.args[0] xsquared = builder.fmul(x, x) y = dsquared_func.args[1] ysquared = builder.fmul(y, y) d2 = builder.fadd(xsquared, ysquared) builder.ret(d2) #print(mod) a = GenericValue.real(Type.double(), 3.0)