diff options
Diffstat (limited to 'bruiser/wasm/TBInit.py')
-rw-r--r-- | bruiser/wasm/TBInit.py | 415 |
1 files changed, 0 insertions, 415 deletions
diff --git a/bruiser/wasm/TBInit.py b/bruiser/wasm/TBInit.py deleted file mode 100644 index f14dfd1..0000000 --- a/bruiser/wasm/TBInit.py +++ /dev/null @@ -1,415 +0,0 @@ -from utils import Colors, init_interpret, ParseFlags -from OpCodes import WASM_OP_Code -from section_structs import Code_Section, Func_Body, WASM_Ins, Resizable_Limits, Memory_Section -from execute import * -import datetime as dti -import os -import sys -import signal - - -# McCabe cyclomatic complexity metric -class Metric(): - def __init__(self, code_section): - self.code_section = code_section - self.metric = [] - self.soc = [] - - def mccabe(self): - soc = 0 - Edges = 1 - Nodes = 1 - for funcs in self.code_section.func_bodies: - for ins in funcs.code: - soc += 1 - #print(repr(ins.opcodeint)) - if ins.opcodeint == 4 or ins.opcodeint == 5 or ins.opcodeint == 12 \ - or ins.opcodeint == 13 or ins.opcodeint == 14: - Nodes += 2 - Edges += 4 - elif ins.opcode == 3: - Nodes += 2 - Edges += 3 - else: - pass - - self.metric.append(Edges - Nodes + 1) - self.soc.append(soc) - soc = 0 - Edges = 1 - Nodes = 1 - - def getMcCabe(self): - return self.metric - - def getSOC(self): - return self.soc - - -# handles the debug option --memdump. dumps the contents of linear memories. -def DumpLinearMems(linear_memories, threshold): - count = int() - strrep = [] - linmem_cnt = int() - for lin_mem in linear_memories: - print('-----------------------------------------') - print(Colors.blue + Colors.BOLD + 'Linear Memory '+ repr(linmem_cnt)+ ' :' + Colors.ENDC) - for byte in lin_mem: - if count >= threshold: - break - if count%16 == 0: - for ch in strrep: - # @DEVI-line feed messes the pretty format up - if ord(ch) != 10: - print(Colors.green + ' ' + ch + Colors.ENDC, end = '') - else: - pass - print() - strrep = [] - print(Colors.cyan + hex(count), ':\t' + Colors.ENDC, end='') - strrep.append(str(chr(byte))) - print(Colors.blue + format(byte, '02x') + ' ' + Colors.ENDC, end='') - else: - strrep += str(chr(byte)) - print(Colors.blue + format(byte, '02x') + ' ' + Colors.ENDC, end='') - count += 1 - count = 0 - print() - - -# handles the debug options --idxspc. dumps the index spaces. -def DumpIndexSpaces(machinestate): - print('-----------------------------------------') - print(Colors.green + 'Function Index Space: ' + Colors.ENDC) - for iter in machinestate.Index_Space_Function: - print(Colors.blue + repr(iter) + Colors.ENDC) - - print('-----------------------------------------') - print(Colors.green + 'Globa Index Space: ' + Colors.ENDC) - for iter in machinestate.Index_Space_Global: - print(Colors.blue + repr(iter) + Colors.ENDC) - - print('-----------------------------------------') - print(Colors.green + 'Linear Memory Index Space: ' + Colors.ENDC) - for iter in machinestate.Index_Space_Linear: - print(Colors.blue + repr(iter) + Colors.ENDC) - - print('-----------------------------------------') - print(Colors.green + 'Table Index Space: ' + Colors.ENDC) - for iter in machinestate.Index_Space_Table: - print(Colors.blue + repr(iter) + Colors.ENDC) - print('-----------------------------------------') - - -# WIP-the Truebit Machine class -class TBMachine(): - def __init__(self): - # bytearray of size PAGE_SIZE - self.Linear_Memory = [] - self.Stack_Label = list() - self.Stack_Label_Height = int() - self.Stack_Control_Flow = list() - self.Stack_Call = list() - self.Stack_Value = list() - self.Stack_Omni = list() - self.Vector_Globals = list() - self.Index_Space_Function = list() - self.Index_Space_Global = list() - self.Index_Space_Linear = list() - self.Index_Space_Table = list() - self.Index_Space_Locals = list() - self.Index_Space_Label = list() - - -# handles the initialization of the WASM machine -class TBInit(): - def __init__(self, module, machinestate): - self.module = module - self.machinestate = machinestate - - # a convenience function that runs the methods of the class. all methods - # can be called separately manually as well. - def run(self): - self.InitFuncIndexSpace() - self.InitGlobalIndexSpace() - self.InitLinearMemoryIndexSpace() - self.InitTableIndexSpace() - self.InitializeLinearMemory() - - def InitFuncIndexSpace(self): - if self.module.import_section is not None: - for iter in self.module.import_section.import_entry: - if iter.kind == 0: - name = str() - for i in iter.field_str: - name += str(chr(i)) - self.machinestate.Index_Space_Function.append(name) - - if self.module.function_section is not None: - for iter in self.module.function_section.type_section_index: - self.machinestate.Index_Space_Function.append(iter) - - def InitGlobalIndexSpace(self): - if self.module.import_section is not None: - for iter in self.module.import_section.import_entry: - if iter.kind == 3: - name = str() - for i in iter.field_str: - name += str(chr(i)) - self.machinestate.Index_Space_Global.append(name) - - if self.module.global_section is not None: - for iter in self.module.global_section.global_variables: - self.machinestate.Index_Space_Global.append(iter.init_expr) - - def InitLinearMemoryIndexSpace(self): - if self.module.import_section is not None: - for iter in self.module.import_section.import_entry: - if iter.kind == 2: - name = str() - for i in iter.field_str: - name += str(chr(i)) - self.machinestate.Index_Space_Linear.append(name) - - if self.module.memory_section is not None: - for iter in self.module.memory_section.memory_types: - self.machinestate.Index_Space_Linear.append(iter.initial) - - def InitTableIndexSpace(self): - if self.module.import_section is not None: - for iter in self.module.import_section.import_entry: - if iter.kind == 1: - name = str() - for i in iter.field_str: - name += str(chr(i)) - self.machinestate.Index_Space_Table.append(name) - - if self.module.table_section is not None: - for iter in self.module.table_section.table_types: - self.machinestate.Index_Space_Table.append(iter.element_type) - - def InitializeLinearMemory(self): - # @DEVI-we could try to pack the data in the linear memory ourselve to - # decrease the machinestate size - if self.module.memory_section is None: - rsz_limits = Resizable_Limits() - self.module.memory_section = Memory_Section() - self.module.memory_section.memory_types = [rsz_limits] - self.module.memory_section.count = 1 - for iter in self.module.memory_section.memory_types: - self.machinestate.Linear_Memory.append(bytearray( - WASM_OP_Code.PAGE_SIZE)) - if self.module.data_section is not None: - for iter in self.module.data_section.data_segments: - count = int() - for byte in iter.data: - self.machinestate.Linear_Memory[iter.index][init_interpret(iter.offset) + count] = byte - count += 1 - - # returns the machinestate - def getInits(self): - return(self.machinestate) - - -# WIP-holds the run-rime data structures for a wasm machine -class RTE(): - def __init__(self): - Stack_Control_Flow = list() - Stack_Value = list() - Vector_Locals = list() - Current_Position = int() - Local_Stacks = list() - - def genFuncLocalStack(func_body): - pass - - -# palceholder for the class that holds the validation functions -class ModuleValidation(): - def __init__(self, module): - self.module = module - - def TypeSection(self): - pass - - def ImportSection(self): - pass - - def FunctionSection(self): - pass - - def TableSection(self): - pass - - def MemorySection(self): - pass - - def GlobalSection(self): - pass - - def ExportSection(self): - pass - - def StartSection(self): - pass - - def ElementSection(self): - pass - - def CodeSection(self): - pass - - def DataSection(self): - pass - - def TBCustom(self): - pass - - def ValidateAll(self): - self.TypeSection() - self.ImportSection() - self.FunctionSection() - self.TableSection() - self.MemorySection() - self.GlobalSection() - self.ExportSection() - self.StartSection() - self.ElementSection() - self.CodeSection() - self.DataSection() - self.TBCustom() - - return(True) - - -# a convinience class that handles the initialization of the wasm machine and -# interpretation of the code. -class VM(): - def __init__(self, modules): - self.modules = modules - self.machinestate = TBMachine() - # @DEVI-FIXME- the first implementation is single-module only - self.init = TBInit(self.modules[0], self.machinestate) - self.init.run() - self.machinestate = self.init.getInits() - self.start_function = Func_Body() - self.ins_cache = WASM_Ins() - self.executewasm = Execute(self.machinestate) - self.totGas = int() - self.metric = Metric(modules[0].code_section) - self.parseflags = None - - def setFlags(self, parseflags): - self.parseflags = parseflags - - def getState(self): - return(self.machinestate) - - def initLocalIndexSpace(self, local_count): - for i in range(0, local_count): - self.machinestate.Index_Space_Locals.append(0) - - def getStartFunctionIndex(self): - if self.modules[0].start_section is None: - if self.parseflags.entry is None: - raise Exception(Colors.red + "module does not have a start section. no function index was provided with the --entry option.quitting..." + Colors.ENDC) - else: - start_index = int(self.parseflags.entry) - else: - print(Colors.green + "found start section: " + Colors.ENDC, end = '') - start_index = self.modules[0].start_section.function_section_index - - print(Colors.blue + Colors.BOLD + "running function at index " + repr(start_index) + Colors.ENDC) - if (start_index > len(self.modules[0].code_section.func_bodies) - 1): - raise Exception(Colors.red + "invalid function index: the function index does not exist." + Colors.ENDC) - return(start_index) - - def getStartFunctionBody(self): - start_index = self.getStartFunctionIndex() - if isinstance(start_index, int): - self.start_function = self.modules[0].code_section.func_bodies[start_index] - elif isinstance(start_index, str): - # we have to import the function from another module/library. we - # assume sys calls are not present.:w - pass - else: - raise Exception(Colors.red + "invalid entry for start function index" + Colors.ENDC) - - def execute(self): - print(Colors.blue + Colors.BOLD + 'running module with code: ' + Colors.ENDC) - for ins in self.start_function.code: - print(Colors.purple + repr(ins.opcode) + ' ' + repr(ins.operands) + Colors.ENDC) - for ins in self.start_function.code: - self.executewasm.getInstruction(ins.opcodeint, ins.operands) - self.executewasm.callExecuteMethod() - self.getState() - - # pre-execution hook - def startHook(self): - if self.parseflags.metric: - for mem in self.modules[0].memory_section.memory_types: - self.executewasm.chargeGasMem(mem.initial) - - self.metric.mccabe() - print(Colors.red + "mccabe: " + repr(self.metric.getMcCabe()) + Colors.ENDC) - print(Colors.red + "soc: " + repr(self.metric.getSOC()) + Colors.ENDC) - - # post-execution hook - def endHook(self): - if self.parseflags.gas: - self.totGas = self.executewasm.getOPGas() - print(Colors.red + "total gas cost: " + repr(self.totGas) + Colors.ENDC) - if self.machinestate.Stack_Omni: - print(Colors.green + "stack top: " + repr(self.machinestate.Stack_Omni.pop()) + Colors.ENDC) - - # a convinience method - def run(self): - self.startHook() - self.getStartFunctionBody() - self.initLocalIndexSpace(self.start_function.local_count) - self.execute() - self.endHook() - - -# a wrapper class for VM. it timeouts instructions that take too long to -# execute. -class Judicator(): - def __int__(self, op_time_table, module): - self.op_time_table = op_time_table - self.vm = VM(modules) - self.vm.getStartFunctionBody() - - def overseer(): - # @DEVI- forking introduces a new source of non-determinism - pid = os.fork() - # child process - if pid == 0: - sys.stdout = open('./jstdout', 'w') - sys.stderr = open('./jstderr', 'w') - self.vm.execute() - sys.exit() - # parent process - if pid > 0: - cpid, status = os.waitpid(pid, 0) - if status == 0: - print('overseer child exited successfully.') - else: - print('overseer child exited with non-zero.') - # pid < 0 - else: - raise Exception(Colors.red + 'could not fork judicator overseer.' + Colors.ENDC) - - def setup(self): - signal.signal(signal.SIGALRM, self.to_sighandler) - - def set_alarm(t): - signal.alaram(t) - - def to_sighandler(signum, frame): - print(Colors.red + "execution time out..." + Colors.ENDC) - raise Exception(Colors.red + "execution time out" + Colors.ENDC) - - def run(self): - self.setup() - self.set_alaram(10) - self.overseer() |