def _phase_1(code): instructions = code.instructions ''' Generate flow graph ''' flow_graph = cfg.generate(instructions) ''' Get usability information ''' use_ins, use_outs = fu.analyse(flow_graph, code.argument_fields, []) ''' Cherry-pick dead instructions ''' instruction_list = [] for _, node in flow_graph.iteritems(): for instruction in node.basic_block: if isinstance(instruction, I.RMV): if is_reserved_or_argument_field(instruction.field.field, code.argument_fields): pass else: if get_rmv_instruction_count(code.instructions, instruction.field.field) < 2: pass elif not (instruction.field.field in use_outs[instruction]): instruction_list.append(instruction) ''' Remove dead instructions from the code ''' for instruction in instruction_list: instructions.remove(instruction)
def _phase_1(code): instructions = code.instructions ''' Generate flow graph ''' flow_graph = cfg.generate(instructions) ''' Get usability information ''' use_ins, use_outs = fu.analyse(flow_graph, code.argument_fields, [I.RMV]) ''' Cherry-pick dead instructions ''' instruction_list = [] for _, node in flow_graph.iteritems(): for instruction in node.basic_block: if isinstance(instruction, I.ADD): if is_reserved_or_argument_field(instruction.field.field, code.argument_fields): pass elif not (instruction.field.field in use_outs[instruction]): instruction_list.append(instruction) ''' Remove dead instructions from the code ''' for instruction in instruction_list: instructions.remove(instruction)
def _phase_2(code): instructions = code.instructions """ Generate flow graph """ flow_graph = cfg.generate(instructions) """ Get reachability information """ reach_ins, reach_outs = fr.analyse(flow_graph, code.argument_fields, [I.ADD]) """ Cherry-pick dead instructions """ instruction_list = [] for _, node in flow_graph.iteritems(): for instruction in node.basic_block: if isinstance(instruction, I.RMV): if is_reserved_or_argument_field(instruction.field.field, code.argument_fields): pass elif not (instruction.field.field in reach_ins[instruction]): instruction_list.append(instruction) """ Remove dead instructions from the code """ for instruction in instruction_list: instructions.remove(instruction)
def _phase_0(code): instructions = code.instructions ''' Generate flow graph ''' flow_graph = cfg.generate(instructions) ''' Get reachability information ''' reach_ins, reach_outs = fr.analyse(flow_graph, code.argument_fields, []) ''' Cherry-pick dead instructions ''' instruction_list = [] for _, node in flow_graph.iteritems(): for instruction in node.basic_block: if isinstance(instruction, I.ADD): if is_reserved_or_argument_field(instruction.field.field, code.argument_fields): pass else: if get_add_instruction_count(code.instructions, instruction.field.field) < 2: pass elif not (instruction.field.field in reach_ins[instruction]): instruction_list.append(instruction) ''' Remove dead instructions from the code ''' for instruction in instruction_list: instructions.remove(instruction)
def cost_Code(code, state): argument_fields = code.argument_fields instructions = code.instructions ''' Generate control flow graph ''' flow_graph = cfg.generate(instructions) ''' Get reaching definitions information (for I.ADD only) ''' reach_def_ins, reach_def_outs = rd.analyse( flow_graph, [], [I.LD, I.OP, I.LDt, I.LKt, I.CRC, I.HSH, I.CNC, I.ATM, I.SEQ]) ''' Get field reachability information ''' reach_ins, reach_outs = fr.analyse( flow_graph, [], [I.LD, I.OP, I.LDt, I.LKt, I.CRC, I.HSH, I.CNC, I.ATM, I.SEQ]) instruction_dict = {} for _, node in flow_graph.iteritems(): for instruction in node.basic_block: if isinstance(instruction, I.ID): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 elif isinstance(instruction, I.DRP): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 elif isinstance(instruction, I.CTR): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 elif isinstance(instruction, I.ADD): pass elif isinstance(instruction, I.RMV): pass elif isinstance(instruction, I.LD): if isinstance(instruction.source, O.Value) or isinstance( instruction.source, O.Field): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 elif isinstance(instruction.source, O.Location): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) * 2 state.latency += 2 elif isinstance(instruction, I.ST): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 elif isinstance(instruction, I.OP): if not (instruction.operator == Op.Mul or instruction.operator == Op.Div): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 else: state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) * 2 state.latency += 2 elif isinstance(instruction, I.PUSH): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 elif isinstance(instruction, I.POP): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 elif isinstance(instruction, I.BR): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 elif isinstance(instruction, I.JMP): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 elif isinstance(instruction, I.LBL): pass elif isinstance(instruction, I.LDt): _, _, table_type = state.tables[instruction.table_id] if table_type == syntax.TableTypeCollection.RAM: state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) * 3 state.latency += 3 else: raise RuntimeError("invalid table type (%s)." % table_type) # Note: # 1) tables are not added in the "area" cost as they will incur a one time cost for the # whole program # 2) it only operates on RAM type elif isinstance(instruction, I.STt): _, _, table_type = state.tables[instruction.table_id] if table_type == syntax.TableTypeCollection.RAM: state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) * 3 state.latency += 3 # elif table_type == syntax.TableTypeCollection.HSH: # latency += 2 elif table_type == syntax.TableTypeCollection.CAM: state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) * 4 state.latency += 4 else: raise RuntimeError("invalid table type (%s)." % table_type) elif isinstance(instruction, I.INCt): _, _, table_type = state.tables[instruction.table_id] state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) if table_type == syntax.TableTypeCollection.RAM: state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) * 3 state.latency += 3 else: raise RuntimeError("invalid table type (%s)." % table_type) elif isinstance(instruction, I.LKt): _, _, table_type = state.tables[instruction.table_id] if table_type == syntax.TableTypeCollection.RAM: state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) * 3 state.latency += 3 # elif table_type == syntax.TableTypeCollection.HSH: # latency += 2 elif table_type == syntax.TableTypeCollection.CAM: state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) * 4 state.latency += 4 else: raise RuntimeError("invalid table type (%s)." % table_type) elif isinstance(instruction, I.CRC): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 elif isinstance(instruction, I.HSH): state.area += get_header_size(reach_ins[instruction], reach_def_ins[instruction], argument_fields) state.latency += 1 elif isinstance(instruction, I.CNC): for code in instruction.codes: cost_Code(code, state) elif isinstance(instruction, I.ATM): cost_Code(instruction.code, state) elif isinstance(instruction, I.SEQ): cost_Code(instruction.code, state)
def _transform(code, exclude_list): instructions = code.instructions ''' Generate flow graph ''' flow_graph = cfg.generate(instructions) ''' Get reaching definitions information (for I.ADD only) ''' reach_def_ins, reach_def_outs = rd.analyse(flow_graph, code.argument_fields, [I.LD, I.OP, I.LDt, I.LKt, I.CRC, I.HSH, I.CNC, I.ATM, I.SEQ]) ''' Get field reachability information ''' reach_ins, reach_outs = fr.analyse(flow_graph, code.argument_fields, exclude_list) ''' Cherry-pick dead instructions ''' instruction_dict = {} for _, node in flow_graph.iteritems(): for instruction in node.basic_block: if isinstance(instruction, I.LD): instruction_dict[instruction] = [] if isinstance(instruction.source, O.Field): if is_reserved_or_argument_field(instruction.source.field, code.argument_fields): pass elif not (instruction.source.field in reach_ins[instruction]): instruction_dict[instruction].append( I.ADD(O.Field(instruction.source.field), get_field_size(reach_def_ins[instruction], instruction.source.field))) if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field(instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in reach_ins[instruction]): instruction_dict[instruction].append( I.ADD(O.Field(instruction.destination.field), get_field_size(reach_def_ins[instruction], instruction.destination.field))) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.ST): instruction_dict[instruction] = [] if isinstance(instruction.source, O.Field): if is_reserved_or_argument_field(instruction.source.field, code.argument_fields): pass elif not (instruction.source.field in reach_ins[instruction]): instruction_dict[instruction].append( I.ADD(O.Field(instruction.source.field), get_field_size(reach_def_ins[instruction], instruction.source.field))) if isinstance(instruction.location, O.Location): if isinstance(instruction.location.location.offset, O.Field): if is_reserved_or_argument_field(instruction.location.location.offset.field, code.argument_fields): pass elif not (instruction.location.location.offset.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.location.location.offset.field), get_field_size(reach_def_ins[instruction], instruction.location.location.offset.field))) if isinstance(instruction.location.location.length, O.Field): if is_reserved_or_argument_field(instruction.location.location.length.field, code.argument_fields): pass elif not (instruction.location.location.length.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.location.location.length.field), get_field_size(reach_def_ins[instruction], instruction.location.location.length.field))) else: raise RuntimeError("invalid %s of location (%s). Should be %s." % (type(instruction.location), instruction.location, O.Location)) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.OP): instruction_dict[instruction] = [] if isinstance(instruction.left_source, O.Field): if is_reserved_or_argument_field(instruction.left_source.field, code.argument_fields): pass elif not (instruction.left_source.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.left_source.field), get_field_size(reach_def_ins[instruction], instruction.left_source.field))) if isinstance(instruction.right_source, O.Field): if is_reserved_or_argument_field(instruction.right_source.field, code.argument_fields): pass elif not (instruction.right_source.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.right_source.field), get_field_size(reach_def_ins[instruction], instruction.right_source.field))) if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field(instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.destination.field), get_field_size(reach_def_ins[instruction], instruction.destination.field))) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.PUSH): instruction_dict[instruction] = [] if isinstance(instruction.location, O.Location): if isinstance(instruction.location.location.offset, O.Field): if is_reserved_or_argument_field(instruction.location.location.offset.field, code.argument_fields): pass elif not (instruction.location.location.offset.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.location.location.offset.field), get_field_size(reach_def_ins[instruction], instruction.location.location.offset.field))) if isinstance(instruction.location.location.length, O.Field): if is_reserved_or_argument_field(instruction.location.location.length.field, code.argument_fields): pass elif not (instruction.location.location.length.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.location.location.length.field), get_field_size(reach_def_ins[instruction], instruction.location.location.length.field))) else: raise RuntimeError("invalid %s of location (%s). Should be %s." % (type(instruction.location), instruction.location, O.Location)) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.POP): instruction_dict[instruction] = [] if isinstance(instruction.location, O.Location): if isinstance(instruction.location.location.offset, O.Field): if is_reserved_or_argument_field(instruction.location.location.offset.field, code.argument_fields): pass elif not (instruction.location.location.offset.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.location.location.offset.field), get_field_size(reach_def_ins[instruction], instruction.location.location.offset.field))) if isinstance(instruction.location.location.length, O.Field): if is_reserved_or_argument_field(instruction.location.location.length.field, code.argument_fields): pass elif not (instruction.location.location.length.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.location.location.length.field), get_field_size(reach_def_ins[instruction], instruction.location.location.length.field))) else: raise RuntimeError("invalid %s of location (%s). Should be %s." % (type(instruction.location), instruction.location, O.Location)) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.BR): instruction_dict[instruction] = [] if isinstance(instruction.left_source, O.Field): if is_reserved_or_argument_field(instruction.left_source.field, code.argument_fields): pass elif not (instruction.left_source.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.left_source.field), get_field_size(reach_def_ins[instruction], instruction.left_source.field))) if isinstance(instruction.right_source, O.Field): if is_reserved_or_argument_field(instruction.right_source.field, code.argument_fields): pass elif not (instruction.right_source.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.right_source.field), get_field_size(reach_def_ins[instruction], instruction.right_source.field))) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.LDt): instruction_dict[instruction] = [] if isinstance(instruction.index, O.Field): if is_reserved_or_argument_field(instruction.index.field, code.argument_fields): pass elif not (instruction.index.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.index.field), get_field_size(reach_def_ins[instruction], instruction.index.field))) if isinstance(instruction.destinations, O.Operands__): for operand in instruction.destinations: if isinstance(operand, O.Field): if is_reserved_or_argument_field(operand.field, code.argument_fields): pass elif not (operand.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(operand.field), get_field_size(reach_def_ins[instruction], operand.field))) else: raise RuntimeError("invalid %s of destinations (%s). Should be %s." % (type(instruction.destinations), instruction.destinations, O.Operands__)) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.STt): instruction_dict[instruction] = [] if isinstance(instruction.index, O.Field): if is_reserved_or_argument_field(instruction.index.field, code.argument_fields): pass elif not (instruction.index.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.index.field), get_field_size(reach_def_ins[instruction], instruction.index.field))) if isinstance(instruction.sources, O.Operands_): for operand in instruction.sources: if isinstance(operand, O.Field): if is_reserved_or_argument_field(operand.field, code.argument_fields): pass elif not (operand.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(operand.field), get_field_size(reach_def_ins[instruction], operand.field))) elif isinstance(instruction.sources, O.OperandsMasks_): for operand, _ in instruction.sources: if isinstance(operand, O.Field): if is_reserved_or_argument_field(operand.field, code.argument_fields): pass elif not (operand.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(operand.field), get_field_size(reach_def_ins[instruction], operand.field))) else: raise RuntimeError("invalid %s of sources (%s). Should be %s or %s." % (type(instruction.sources), instruction.sources, O.Operands_, O.OperandsMasks_)) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.INCt): instruction_dict[instruction] = [] if isinstance(instruction.index, O.Field): if is_reserved_or_argument_field(instruction.index.field, code.argument_fields): pass elif not (instruction.index.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.index.field), get_field_size(reach_def_ins[instruction], instruction.index.field))) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.LKt): instruction_dict[instruction] = [] if isinstance(instruction.sources, O.Operands_): for operand in instruction.sources: if isinstance(operand, O.Field): if is_reserved_or_argument_field(operand.field, code.argument_fields): pass elif not (operand.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(operand.field), get_field_size(reach_def_ins[instruction], operand.field))) else: raise RuntimeError("invalid %s of sources (%s). Should be %s." % (type(instruction.sources), instruction.sources, O.Operands_)) if isinstance(instruction.index, O.Field): if is_reserved_or_argument_field(instruction.index.field, code.argument_fields): pass elif not (instruction.index.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.index.field), get_field_size(reach_def_ins[instruction], instruction.index.field))) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.CRC): instruction_dict[instruction] = [] if isinstance(instruction.sources, O.Operands_): for operand in instruction.sources: if isinstance(operand, O.Field): if is_reserved_or_argument_field(operand.field, code.argument_fields): pass elif not (operand.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(operand.field), get_field_size(reach_def_ins[instruction], operand.field))) else: raise RuntimeError("invalid %s of sources (%s). Should be %s." % (type(instruction.sources), instruction.sources, O.Operands_)) if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field(instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.destination.field), get_field_size(reach_def_ins[instruction], instruction.destination.field))) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.HSH): instruction_dict[instruction] = [] if isinstance(instruction.sources, O.Operands_): for operand in instruction.sources: if isinstance(operand, O.Field): if is_reserved_or_argument_field(operand.field, code.argument_fields): pass elif not (operand.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(operand.field), get_field_size(reach_def_ins[instruction], operand.field))) else: raise RuntimeError("invalid %s of sources (%s). Should be %s." % (type(instruction.sources), instruction.sources, O.Operands_)) if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field(instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(instruction.destination.field), get_field_size(reach_def_ins[instruction], instruction.destination.field))) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.CNC): instruction_dict[instruction] = [] if isinstance(instruction.codes, I.Codes): for _code in instruction.codes: for field in _code.argument_fields: if is_reserved_or_argument_field(field, code.argument_fields): pass elif not (field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(field), get_field_size(reach_def_ins[instruction], field))) else: raise RuntimeError("invalid %s of codes (%s). Should be %s." % (type(instruction.codes), instruction.codes, I.Codes)) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.ATM): instruction_dict[instruction] = [] if isinstance(instruction.code, I.Code): for field in instruction.code.argument_fields: if is_reserved_or_argument_field(field, code.argument_fields): pass elif not (field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(field), get_field_size(reach_def_ins[instruction], field))) else: raise RuntimeError("invalid %s of code (%s). Should be %s." % (type(instruction.code), instruction.code, I.Code)) if not instruction_dict[instruction]: del instruction_dict[instruction] elif isinstance(instruction, I.SEQ): instruction_dict[instruction] = [] if isinstance(instruction.code, I.Code): for field in instruction.code.argument_fields: if is_reserved_or_argument_field(field, code.argument_fields): pass elif not (field in reach_ins[instruction]): instruction_dict[instruction].append(I.ADD( O.Field(field), get_field_size(reach_def_ins[instruction], field))) else: raise RuntimeError("invalid %s of sources (%s). Should be %s." % (type(instruction.code), instruction.code, I.Code)) if not instruction_dict[instruction]: del instruction_dict[instruction] ''' Add new add instructions in the code ''' for instruction, _instructions in instruction_dict.iteritems(): index = instructions.index(instruction) for i in range(0, len(_instructions)): instructions.insert(index + i, _instructions[i])
def _setup(self): flow_graph = cfg.generate(self.instructions) ''' Setting connections with in basic blocks ''' for label, node in flow_graph.iteritems(): if label == syntax.Label('$entry') or label == syntax.Label('$exit'): continue next_instruction = None for instruction in node.basic_block[::-1]: if (isinstance(instruction, I.ATM) or isinstance(instruction, I.SEQ) or isinstance(instruction, I.CNC)): self._instructions[instruction] = GroupProcess(instruction, self.tables) else: self._instructions[instruction] = PrimitiveProcess(instruction) if next_instruction: self._instructions[instruction].output_interfaces[syntax.Label('')] = \ self._instructions[next_instruction].input_interface next_instruction = instruction ''' Setting up connections across basic blocks ''' for label, node in flow_graph.iteritems(): last_instruction = node.basic_block[-1] for successor_label in node.successors: first_instruction = flow_graph[successor_label].basic_block[0] if label == syntax.Label('$entry'): # if successor_label == Label('$exit'): # self.input_interface = self.output_interface # else: self._input_interface = self._instructions[first_instruction].input_interface # Note: this should always be no more than one else: if successor_label == syntax.Label('$exit'): self._instructions[last_instruction].output_interfaces[ syntax.Label('')] = self._output_interface else: if isinstance(last_instruction, I.BR) or isinstance(last_instruction, I.JMP): if last_instruction.label == successor_label: self._instructions[last_instruction].output_interfaces[last_instruction.label] = \ self._instructions[first_instruction].input_interface else: self._instructions[last_instruction].output_interfaces[syntax.Label('')] = \ self._instructions[first_instruction].input_interface else: self._instructions[last_instruction].output_interfaces[syntax.Label('')] = \ self._instructions[first_instruction].input_interface ''' Connect tables with instructions ''' for instruction in self._instructions: if isinstance(instruction, I.LDt): table = self.tables[instruction.table_id] self._instructions[instruction].table_interface.output_interface = table.input_interface table.output_interfaces[id(instruction)] = \ self._instructions[instruction].table_interface.input_interface elif isinstance(instruction, I.STt): table = self.tables[instruction.table_id] self._instructions[instruction].table_interface.output_interface = table.input_interface table.output_interfaces[id(instruction)] = \ self._instructions[instruction].table_interface.input_interface elif isinstance(instruction, I.INCt): table = self.tables[instruction.table_id] self._instructions[instruction].table_interface.output_interface = table.input_interface table.output_interfaces[id(instruction)] = \ self._instructions[instruction].table_interface.input_interface elif isinstance(instruction, I.LKt): table = self.tables[instruction.table_id] self._instructions[instruction].table_interface.output_interface = table.input_interface table.output_interfaces[id(instruction)] = \ self._instructions[instruction].table_interface.input_interface self._is_setup = True
def _phase_0(code): instructions = code.instructions ''' Generate flow graph ''' flow_graph = cfg.generate(instructions) ''' Get liveness information ''' live_ins, live_outs = li.analyse(flow_graph, code.argument_fields, [I.ADD, I.RMV]) ''' Cherry-pick dead instructions ''' instruction_list = [] for _, node in flow_graph.iteritems(): for instruction in node.basic_block: # I.ID # I.DRP # I.CTR # I.ADD # I.RMV if isinstance(instruction, I.LD): if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field( instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in live_outs[instruction]): instruction_list.append(instruction) # I.ST elif isinstance(instruction, I.OP): if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field( instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in live_outs[instruction]): instruction_list.append(instruction) # I.PUSH # I.POP # I.BR # I.JMP # I.LBL elif isinstance(instruction, I.LDt): check_list = [] for destination in instruction.destinations: if isinstance(destination, O.Field): if is_reserved_or_argument_field( destination.field, code.argument_fields): check_list.append(False) else: check_list.append(True if not ( destination.field in live_outs[instruction] ) else False) if check_list and all(check_list): instruction_list.append(instruction) # I.STt # I.INCt elif isinstance(instruction, I.LKt): if isinstance(instruction.index, O.Field): if is_reserved_or_argument_field(instruction.index.field, code.argument_fields): pass elif not (instruction.index.field in live_outs[instruction]): instruction_list.append(instruction) elif isinstance(instruction, I.CRC): if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field( instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in live_outs[instruction]): instruction_list.append(instruction) elif isinstance(instruction, I.HSH): if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field( instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in live_outs[instruction]): instruction_list.append(instruction) # I.HLT # I.CNC # I.ATM # I.SEQ # TODO: add support for group instructions, above. ''' Remove dead instructions from the code ''' for instruction in instruction_list: instructions.remove(instruction)
O.Value(Value(1, Size(16))), ), I.JMP(Label('LBL_0')), I.LBL(Label('LBL_HLT')), I.LD(O.Field(Field('outport_bitmap')), O.Field(Field('reg0'))), I.HLT())) return Policy(decls, code) # Testing if __name__ == "__main__": policy = main() # CFG if False: import netasm.netasm.core.graphs.control_flow_graph as cfg graph = cfg.generate(policy.code.instructions) print graph # Cost if False: from netasm.netasm import cost area, latency = cost.cost_Policy(policy) print area, latency # Execute if True: from netasm.netasm import execute policy = execute.Execute(policy) state = execute.State(execute.Header(), execute.Packet(1000))
def _phase_0(code): instructions = code.instructions """ Generate flow graph """ flow_graph = cfg.generate(instructions) """ Get liveness information """ live_ins, live_outs = li.analyse(flow_graph, code.argument_fields, [I.ADD, I.RMV]) """ Cherry-pick dead instructions """ instruction_list = [] for _, node in flow_graph.iteritems(): for instruction in node.basic_block: # I.ID # I.DRP # I.CTR # I.ADD # I.RMV if isinstance(instruction, I.LD): if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field(instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in live_outs[instruction]): instruction_list.append(instruction) # I.ST elif isinstance(instruction, I.OP): if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field(instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in live_outs[instruction]): instruction_list.append(instruction) # I.PUSH # I.POP # I.BR # I.JMP # I.LBL elif isinstance(instruction, I.LDt): check_list = [] for destination in instruction.destinations: if isinstance(destination, O.Field): if is_reserved_or_argument_field(destination.field, code.argument_fields): check_list.append(False) else: check_list.append(True if not (destination.field in live_outs[instruction]) else False) if check_list and all(check_list): instruction_list.append(instruction) # I.STt # I.INCt elif isinstance(instruction, I.LKt): if isinstance(instruction.index, O.Field): if is_reserved_or_argument_field(instruction.index.field, code.argument_fields): pass elif not (instruction.index.field in live_outs[instruction]): instruction_list.append(instruction) elif isinstance(instruction, I.CRC): if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field(instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in live_outs[instruction]): instruction_list.append(instruction) elif isinstance(instruction, I.HSH): if isinstance(instruction.destination, O.Field): if is_reserved_or_argument_field(instruction.destination.field, code.argument_fields): pass elif not (instruction.destination.field in live_outs[instruction]): instruction_list.append(instruction) # I.HLT # I.CNC # I.ATM # I.SEQ # TODO: add support for group instructions, above. """ Remove dead instructions from the code """ for instruction in instruction_list: instructions.remove(instruction)