def generate(self, **kargs): thread_groups = self.queryThreadGroup() if len(thread_groups) != 2: self.error('Unexpected thread group count; Expected=%d, Actual=%d' % (2, len(thread_groups))) total_thread_count = self.getThreadNumber() for thread_group in thread_groups: thread_constr = ConstraintSet(thread_group[2]) if thread_constr.size() != (total_thread_count // 2): self.error('Unexpected group thread count; Expected=%d, Actual=%d' % ((total_thread_count // 2), thread_constr.size())) for thread_id in range(total_thread_count // 2): group_id = self.getThreadGroupId(thread_id) if group_id != 0: self.error('Unexpected thread group ID; Expected=%d, Actual=%d' % (0, group_id)) for thread_id in range(total_thread_count // 2, total_thread_count): group_id = self.getThreadGroupId(thread_id) if group_id != 1: self.error('Unexpected thread group ID; Expected=%d, Actual=%d' % (0, group_id)) free_threads = self.getFreeThreads() if len(free_threads) != 0: self.error('Unexpected free thread count; Expected=%d, Actual=%d' % (0, len(free_threads)))
def generate(self, **kargs): thread_groups = self.queryThreadGroup() if len(thread_groups) != 2: self.error( "Unexpected thread group count; Expected=%d, Actual=%d" % (2, len(thread_groups)) ) total_thread_count = self.getThreadNumber() for thread_group in thread_groups: thread_constr = ConstraintSet(thread_group[2]) if thread_constr.size() != (total_thread_count // 2): self.error( "Unexpected group thread count; Expected=%d, Actual=%d" % ((total_thread_count // 2), thread_constr.size()) ) for thread_id in range(0, self.getThreadNumber(), 2): group_id_a = self.getThreadGroupId(thread_id) group_id_b = self.getThreadGroupId(thread_id + 1) if group_id_a == group_id_b: self.error( "Expected Thread %d (Group ID %d) to have a different " "group ID from Thread %d (Group ID %d)" % (thread_id, group_id_a, (thread_id + 1), group_id_b) ) free_threads = self.getFreeThreads() if len(free_threads) != 0: self.error( "Unexpected free thread count; Expected=%d, Actual=%d" % (0, len(free_threads)) )
def generate(self, **kargs): thread_groups = self.queryThreadGroup() if len(thread_groups) != 1: self.error( "Unexpected thread group count; Expected=%d, Actual=%d" % (1, len(thread_groups))) total_thread_count = self.getThreadNumber() thread_constr = ConstraintSet(thread_groups[0][2]) if thread_constr.size() != total_thread_count: self.error( "Unexpected group thread count; Expected=%d, Actual=%d" % (total_thread_count, thread_constr.size())) thread_groups = self.queryThreadGroup(1) if len(thread_groups) != 0: self.error("Unexpectedly retrieved nonexistent thread group %d" % 1) group_id = self.getThreadGroupId() if group_id != 0: self.error("Unexpected thread group ID; Expected=%d, Actual=%d" % (0, group_id)) # The thread count should not be a valid thread ID; e.g. if there are # 16 threads, the largest valid thread ID is 15 group_id = self.getThreadGroupId(total_thread_count) if group_id is not None: self.error("Unexpected thread group ID for nonexistent thread; " "Expected=None, Actual=%d" % group_id) free_threads = self.getFreeThreads() if len(free_threads) != 0: self.error("Unexpected free thread count; Expected=%d, Actual=%d" % (0, len(free_threads)))
def generate(self, **kargs): init_size = 256 init_addr = self.genVA(Size=init_size, Align=init_size, Type="D") addr_constr = ConstraintSet(init_addr, (init_addr + init_size - 1)) for _ in range(RandomUtils.random32(50, 100)): size = RandomUtils.random32(8, 32) alignment = self.choice((1, 2, 4, 8, 16, 32)) addr = self.genVA(Size=size, Align=alignment, Type="D", Range=str(addr_constr)) if not addr_constr.containsValue(addr): self.error("Virtual address 0x%x was generated outside of the " "specified range %s" % (addr, addr_constr))
def _generateInstructionParameters(self): instr_params = {} if RandomUtils.random32(0, 1) == 1: instr_params["NoPreamble"] = 1 target_choice = RandomUtils.random32(0, 2) if target_choice == 1: target_addr = self.genVA(Size=512, Align=8, Type="D") self._mTargetAddrConstr = ConstraintSet(target_addr) instr_params["LSTarget"] = str(self._mTargetAddrConstr) elif target_choice == 2: va_range_size = RandomUtils.random32() min_target_addr = self.genVA(Size=512, Align=8, Type="D") max_target_addr = mask_to_size( (min_target_addr + RandomUtils.random32()), 64) self._mTargetAddrConstr = ConstraintSet(min_target_addr, max_target_addr) instr_params["LSTarget"] = str(self._mTargetAddrConstr) return instr_params
def generate(self, **kargs): init_size = 256 init_addr = self.genVA(Size=init_size, Align=init_size, Type='D') addr_constr = ConstraintSet(init_addr, (init_addr + init_size - 1)) for _ in range(RandomUtils.random32(50, 100)): instr_params = {'LSTarget': str(addr_constr), 'NoSkip': 1} if RandomUtils.random32(0, 1) == 1: instr_params['NoPreamble'] = 1 else: instr_params['UsePreamble'] = 1 instr_id = self.genInstruction( self.choice(('LD##RISCV', 'SD##RISCV')), instr_params) instr_record = self.queryInstructionRecord(instr_id) if not addr_constr.containsValue(instr_record['LSTarget']): self.error( 'Target address 0x%x was generated outside of the specified range %s' % (addr, addr_constr))
def generate(self, **kargs): init_size = 256 init_addr = self.genVA(Size=init_size, Align=init_size, Type="D") addr_constr = ConstraintSet(init_addr, (init_addr + init_size - 1)) for _ in range(RandomUtils.random32(50, 100)): instr_params = {"LSTarget": str(addr_constr), "NoSkip": 1} if RandomUtils.random32(0, 1) == 1: instr_params["NoPreamble"] = 1 else: instr_params["UsePreamble"] = 1 if self.getGlobalState("AppRegisterWidth") == 32: instr_id = self.genInstruction( self.choice(("LW##RISCV", "SW##RISCV")), instr_params) else: instr_id = self.genInstruction( self.choice(("LD##RISCV", "SD##RISCV")), instr_params) instr_record = self.queryInstructionRecord(instr_id) if not addr_constr.containsValue(instr_record["LSTarget"]): self.error("Target address 0x%x was generated outside of the" "specified range %s" % (addr, addr_constr))
def _getHandlerMemoryConstraint(self): # Need to ensure the handler memory doesn't intersect the boot region # or initial PC of any thread handler_memory_constr = ConstraintSet(0, 0xFFFFFFFFFFFFFFFF) for thread_id in range(self.getThreadNumber()): handler_memory_constr.subRange( PcConfig.get_boot_pc(thread_id), (PcConfig.get_boot_pc(thread_id) + PcConfig.get_boot_region_size() - 1), ) handler_memory_constr.subValue(PcConfig.get_initial_pc(thread_id)) return handler_memory_constr
class VectorLoadStoreTestSequence(VectorTestSequence): def __init__(self, aGenThread, aName=None): super().__init__(aGenThread, aName) self._mUnalignedAllowed = False self._mTargetAddrConstr = None # Set up the environment prior to generating the test instructions. def _setUpTest(self): if RandomUtils.random32(0, 1) == 1: choices_mod = ChoicesModifier(self.genThread) choice_weights = {"Aligned": 80, "Unaligned": 20} choices_mod.modifyOperandChoices("Data alignment", choice_weights) choices_mod.commitSet() self._mUnalignedAllowed = True # Return parameters to be passed to Sequence.genInstruction(). def _getInstructionParameters(self): self._mTargetAddrConstr = None instr_params = {} if RandomUtils.random32(0, 1) == 1: if RandomUtils.random32(0, 1) == 1: instr_params["NoPreamble"] = 1 target_choice = RandomUtils.random32(0, 2) if target_choice == 1: target_addr = self.genVA(Size=512, Align=8, Type="D") self._mTargetAddrConstr = ConstraintSet(target_addr) instr_params["LSTarget"] = str(self._mTargetAddrConstr) elif target_choice == 2: va_range_size = RandomUtils.random32() min_target_addr = self.genVA(Size=512, Align=8, Type="D") max_target_addr = mask_to_size( (min_target_addr + RandomUtils.random32()), 64) self._mTargetAddrConstr = ConstraintSet( min_target_addr, max_target_addr) instr_params["LSTarget"] = str(self._mTargetAddrConstr) return instr_params # Return true if it is permissible for the generation to skip this # instruction. # # @param aInstr The name of the instruction. # @param aInstrParams The parameters passed to Sequence.genInstruction(). def _isSkipAllowed(self, aInstr, aInstrParams): if aInstrParams or (self._calculateEmul(aInstr) > 8): return True return False # Verify additional aspects of the instruction generation and execution. # # @param aInstr The name of the instruction. # @param aInstrRecord A record of the generated instruction. def _performAdditionalVerification(self, aInstr, aInstrRecord): if ((self._mTargetAddrConstr is not None) and (0x2 not in self._getAllowedExceptionCodes(aInstr)) and (not self._mTargetAddrConstr.containsValue( aInstrRecord["LSTarget"]))): self.error("Target address 0x%x was outside of the specified " "constraint %s" % (aInstrRecord["LSTarget"], self._mTargetAddrConstr)) # Get allowed exception codes. # # @param aInstr The name of the instruction. def _getAllowedExceptionCodes(self, aInstr): allowed_except_codes = set() if self._mUnalignedAllowed: allowed_except_codes.add(0x4) allowed_except_codes.add(0x6) if self._calculateEmul(aInstr) > 8: allowed_except_codes.add(0x2) return allowed_except_codes # Calculate EMUL for the given instruction. # # @param aInstr The name of the instruction. def _calculateEmul(self, aInstr): eew = self._getEew(aInstr) (vlmul_val, valid) = self.readRegister("vtype", field="VLMUL") self.assertValidRegisterValue("vtype", valid) lmul = self.calculateLmul(vlmul_val) (vsew_val, valid) = self.readRegister("vtype", field="VSEW") self.assertValidRegisterValue("vtype", valid) sew = self.calculateLmul(vsew_val) return round((eew / sew) * lmul) # Determine EEW for the given instruction. # # @param aInstr The name of the instruction. def _getEew(self, aInstr): match = re.fullmatch(r"V[A-Z]+(\d+)\.V\#\#RISCV", aInstr) return int(match.group(1))
class VectorLoadStoreTestSequence(VectorTestSequence): def __init__(self, aGenThread, aName=None): super().__init__(aGenThread, aName) self._mUnalignedAllowed = False self._mTargetAddrConstr = None ## Set up the environment prior to generating the test instructions. def _setUpTest(self): if RandomUtils.random32(0, 1) == 1: choices_mod = ChoicesModifier(self.genThread) choice_weights = {'Aligned': 80, 'Unaligned': 20} choices_mod.modifyOperandChoices('Data alignment', choice_weights) choices_mod.commitSet() self._mUnalignedAllowed = True ## Return parameters to be passed to Sequence.genInstruction(). def _getInstructionParameters(self): self._mTargetAddrConstr = None instr_params = {} if RandomUtils.random32(0, 1) == 1: if RandomUtils.random32(0, 1) == 1: instr_params['NoPreamble'] = 1 target_choice = RandomUtils.random32(0, 2) if target_choice == 1: target_addr = self.genVA(Size=512, Align=8, Type='D') self._mTargetAddrConstr = ConstraintSet(target_addr) instr_params['LSTarget'] = str(self._mTargetAddrConstr) elif target_choice == 2: va_range_size = RandomUtils.random32() min_target_addr = self.genVA(Size=512, Align=8, Type='D') max_target_addr = mask_to_size( (min_target_addr + RandomUtils.random32()), 64) self._mTargetAddrConstr = ConstraintSet( min_target_addr, max_target_addr) instr_params['LSTarget'] = str(self._mTargetAddrConstr) return instr_params ## Return true if it is permissible for the generation to skip this instruction. # # @param aInstr The name of the instruction. # @param aInstrParams The parameters passed to Sequence.genInstruction(). def _isSkipAllowed(self, aInstr, aInstrParams): if aInstrParams or (self._calculateEmul(aInstr) > 8): return True return False ## Verify additional aspects of the instruction generation and execution. # # @param aInstr The name of the instruction. # @param aInstrRecord A record of the generated instruction. def _performAdditionalVerification(self, aInstr, aInstrRecord): if (self._mTargetAddrConstr is not None) and (not self._mTargetAddrConstr.containsValue( aInstrRecord['LSTarget'])): self.error( 'Target address 0x%x was outside of the specified constraint %s' % (aInstrRecord['LSTarget'], self._mTargetAddrConstr)) ## Get allowed exception codes. # # @param aInstr The name of the instruction. def _getAllowedExceptionCodes(self, aInstr): allowed_except_codes = set() if self._mUnalignedAllowed: allowed_except_codes.add(0x4) allowed_except_codes.add(0x6) if self._calculateEmul(aInstr) > 8: allowed_except_codes.add(0x2) # TODO(Noah): Remove the line below permitting store page fault exceptions when the page # descriptor generation is improved. Currently, we are generating read-only pages for load # instructions, which is causing subsequent store instructions to the same page to fault. allowed_except_codes.add(0xF) return allowed_except_codes ## Calculate EMUL for the given instruction. # # @param aInstr The name of the instruction. def _calculateEmul(self, aInstr): eew = self._getEew(aInstr) (vlmul_val, valid) = self.readRegister('vtype', field='VLMUL') self.assertValidRegisterValue('vtype', valid) lmul = self.calculateLmul(vlmul_val) (vsew_val, valid) = self.readRegister('vtype', field='VSEW') self.assertValidRegisterValue('vtype', valid) sew = self.calculateLmul(vsew_val) return round((eew / sew) * lmul) ## Determine EEW for the given instruction. # # @param aInstr The name of the instruction. def _getEew(self, aInstr): match = re.fullmatch(r'V[A-Z]+(\d+)\.V\#\#RISCV', aInstr) return int(match.group(1))
def generate(self, **kargs): if self.getThreadGroupId() != 0: return thread_groups = self.queryThreadGroup(0) assert_equal(len(thread_groups), 1, "Unexpected thread group count") thread_constr = ConstraintSet(thread_groups[0][2]) assert_equal(thread_constr.size(), 1, "Unexpected group thread count") expected_free_thread_count = self.getThreadNumber() - 1 free_threads = self.getFreeThreads() assert_equal(len(free_threads), expected_free_thread_count, "Unexpected free thread count") # Allocate two threads into one group randomly self.partitionThreadGroup("Random", group_num=1, group_size=2) expected_free_thread_count -= 2 thread_groups = self.queryThreadGroup() assert_equal(len(thread_groups), 2, "Unexpected thread group count") thread_constr_0 = ConstraintSet(thread_groups[0][2]) assert_equal(thread_constr_0.size(), 1, "Unexpected group thread count") thread_constr_1 = ConstraintSet(thread_groups[1][2]) assert_equal(thread_constr_1.size(), 2, "Unexpected group thread count") free_threads = self.getFreeThreads() assert_equal(len(free_threads), expected_free_thread_count, "Unexpected free thread count") free_thread_sample = self.sampleFreeThreads(5) group_id = thread_groups[1][0] self.setThreadGroup(group_id, "Endless Loop", free_thread_sample) expected_free_thread_count = expected_free_thread_count + 2 - 5 thread_groups = self.queryThreadGroup(group_id) assert_equal(len(thread_groups), 1, "Unexpected thread group count") thread_constr = ConstraintSet(thread_groups[0][2]) assert_equal(thread_constr.size(), 5, "Unexpected group thread count") free_threads = self.getFreeThreads() assert_equal(len(free_threads), expected_free_thread_count, "Unexpected free thread count")
def generate(self, **kargs): constr_a = ConstraintSet(0x23, 0x87) if constr_a.isEmpty(): self.error('Constraint %s reported as empty.' % constr_a) if constr_a.size() != 101: self.error( 'Constraint %s reported incorrect size; Expected = 101, Actual = %d' % (constr_a, constr_a.size())) val = constr_a.chooseValue() if (val < 0x23) or (val > 0x87): self.error('Chosen value %d lies outside of constraint %s' % (val, constr_a)) constr_a.addRange(0x35, 0x100) if str(constr_a) != '0x23-0x100': self.error('Constraint %s didn\'t add range correctly.' % constr_a) constr_a.subRange(0x4F, 0x6F) if str(constr_a) != '0x23-0x4e,0x70-0x100': self.error('Constraint %s didn\'t subtract range correctly.' % constr_a) constr_b = ConstraintSet('0x18, 0x22-0x5C') constr_b.mergeConstraintSet(constr_a) if str(constr_b) != '0x18,0x22-0x5c,0x70-0x100': self.error( 'Constraint %s didn\'t merge with constraint %s correctly.' % (constr_b, constr_a)) constr_c = ConstraintSet(0x5B) constr_c.applyConstraintSet(constr_a) if not constr_c.isEmpty(): self.error('Constraint %s didn\'t apply constraint %s correctly.' % (constr_c, constr_a)) constr_d = ConstraintSet(constr_a) if constr_d != constr_a: self.error( 'Constraint %s didn\'t copy from constraint %s correctly.' % (constr_d, constr_a))
def _testConstraintSetMethods(self): for _ in range(5): constr_a = ConstraintSet(0xF9B3, 0x207CE) if constr_a.isEmpty(): self.error("Constraint %s reported as empty." % constr_a) if constr_a.size() != 69148: self.error( "Constraint %s reported incorrect size; Expected = 69148, " "Actual = %d" % (constr_a, constr_a.size())) val = constr_a.chooseValue() if (val < 0xF9B3) or (val > 0x207CE): self.error("Chosen value %d lies outside of constraint %s" % (val, constr_a)) constr_a.addRange(0xE700, 0xE800) if str(constr_a) != "0xe700-0xe800,0xf9b3-0x207ce": self.error("Constraint %s didn't add range correctly." % constr_a) constr_a.subRange(0xE780, 0x1F390) if str(constr_a) != "0xe700-0xe77f,0x1f391-0x207ce": self.error("Constraint %s didn't subtract range correctly." % constr_a) constr_b = ConstraintSet(0x20800) constr_b.mergeConstraintSet(constr_a) if str(constr_b) != "0xe700-0xe77f,0x1f391-0x207ce,0x20800": self.error( "Constraint %s didn't merge with constraint %s correctly." % (constr_b, constr_a)) constr_c = ConstraintSet("0x20000-0x20600,0x20800") constr_c.applyConstraintSet(constr_a) if str(constr_c) != "0x20000-0x20600": self.error( "Constraint %s didn't apply constraint %s correctly." % (constr_c, constr_a)) constr_d = ConstraintSet(constr_a) if constr_d != constr_a: self.error( "Constraint %s didn't copy from constraint %s correctly." % (constr_d, constr_a))
def _recordMemoryAttributes(self, mem_attributes, start_addr, end_addr): for arch_mem_attr in mem_attributes.split(","): addr_ranges = self._mMemAttrRanges.setdefault( arch_mem_attr, ConstraintSet()) addr_ranges.addRange(start_addr, end_addr)
def generate(self, **kargs): group_id = self.getThreadGroupId() if group_id == 0: thread_groups = self.queryThreadGroup(0) if len(thread_groups) != 1: self.error( 'Unexpected thread group count; Expected=%d, Actual=%d' % (1, len(thread_groups))) thread_constr = ConstraintSet(thread_groups[0][2]) if thread_constr.size() != 1: self.error( 'Unexpected group thread count; Expected=%d, Actual=%d' % (1, thread_constr.size())) expected_free_thread_count = self.getThreadNumber() - 1 free_threads = self.getFreeThreads() if len(free_threads) != expected_free_thread_count: self.error( 'Unexpected free thread count; Expected=%d, Actual=%d' % (expected_free_thread_count, len(free_threads))) # Allocate two threads into one group randomly self.partitionThreadGroup('Random', group_num=1, group_size=2) expected_free_thread_count -= 2 thread_groups = self.queryThreadGroup() if len(thread_groups) != 2: self.error( 'Unexpected thread group count; Expected=%d, Actual=%d' % (2, len(thread_groups))) thread_constr_0 = ConstraintSet(thread_groups[0][2]) if thread_constr_0.size() != 1: self.error( 'Unexpected group thread count; Expected=%d, Actual=%d' % (1, thread_constr_0.size())) thread_constr_1 = ConstraintSet(thread_groups[1][2]) if thread_constr_1.size() != 2: self.error( 'Unexpected group thread count; Expected=%d, Actual=%d' % (2, thread_constr_1.size())) free_threads = self.getFreeThreads() if len(free_threads) != expected_free_thread_count: self.error( 'Unexpected free thread count; Expected=%d, Actual=%d' % (expected_free_thread_count, len(free_threads))) free_thread_sample = self.sampleFreeThreads(5) group_id = thread_groups[1][0] self.setThreadGroup(group_id, 'Endless Loop', free_thread_sample) expected_free_thread_count = expected_free_thread_count + 2 - 5 thread_groups = self.queryThreadGroup(group_id) if len(thread_groups) != 1: self.error( 'Unexpected thread group count; Expected=%d, Actual=%d' % (1, len(thread_groups))) thread_constr = ConstraintSet(thread_groups[0][2]) if thread_constr.size() != 5: self.error( 'Unexpected group thread count; Expected=%d, Actual=%d' % (5, thread_constr.size())) free_threads = self.getFreeThreads() if len(free_threads) != expected_free_thread_count: self.error( 'Unexpected free thread count; Expected=%d, Actual=%d' % (expected_free_thread_count, len(free_threads)))