Example #1
0
    def __init__(self, file="", filename="", graphexport=False, dbg_enabled: bool = False):
        Debug.__init__(self, dbg_enabled)

        # PROTO DATA OBJECTS ####
        self.constNode: Dict[str, CommonTree] = {}
        self.networkNode: List[CommonTree] = []

        # Architecture nodes
        self.cache_node: PCCObject = None
        self.dir_node: PCCObject = None
        self.mem_node: PCCObject = None

        self.msgNode: List[PCCObject] = []
        self.msgTypes: List[str] = []
        self.dataMsgTypes: List[str] = []  # Data msg type names, should be included in the message

        self.archNode: Dict[str, List[Transaction]] = {}
        self.stableStates: Dict[str, List[str]] = {}        # [arch_name, List[stable_state_names]
        self.initStateNodes: Dict[str, str] = {}                # This is missing

        if file and filename:
            self.filename = filename
            lexer = ProtoCCLexer(antlr3.StringStream(file))
            parser = ProtoCCParser(antlr3.CommonTokenStream(lexer))
            tree = parser.document().getTree()
            new_tree_base = copy_tree(tree)
            self.pdebug(new_tree_base.toStringTree())
            self._ParseNodes(new_tree_base)

            self.perror("Accesses for SSP not defined", self.checkAccessBehaviourDefined())
            self.perror("Terminal states detected in SSP", self.checkAllStatesReachable())

            if graphexport:
                self._dArch()
Example #2
0
    def __init__(self, template_dir, debug_enable: bool = False):
        GlobalVariables.__init__(self)
        Debug.__init__(self, debug_enable)

        GenConst.__init__(self, template_dir)
        GenEnums.__init__(self, template_dir)
        GenObjectSets.__init__(self, template_dir)
        GenNetworkObj.__init__(self, template_dir)
        GenAccessType.__init__(self, template_dir)
        GenMachObj.__init__(self, template_dir)
        GenLockType.__init__(self, template_dir)
        GenVars.__init__(self, template_dir)
        GenLockFunc.__init__(self, template_dir)
        GenNetworkFunc.__init__(self, template_dir)
        GenAccessFunc.__init__(self, template_dir)
        GenFSMFuncObj.__init__(self, template_dir)

        GenAccessRuleset.__init__(self, template_dir)
        GenAccessSendFunc.__init__(self, template_dir)

        GenModStateFunc.__init__(self, template_dir)

        GenNetworkRules.__init__(self, template_dir)
        GenStartStates.__init__(self, template_dir)
        GenInvar.__init__(self, template_dir)
Example #3
0
    def __init__(self,
                 level: Level,
                 config,
                 dbg_term: bool = False,
                 dbg_graph: bool = False):

        ProtoStalling.__init__(self)
        ProtoNonStalling.__init__(self)
        ProtoDir.__init__(self)
        ProtoAccessAssign.__init__(self)
        Debug.__init__(self, dbg_term)
        self.dbg_graph = dbg_graph

        self.debug_all_generated_states = []

        self.level = level

        self.parser = level.parser

        self.datamsgs = level.parser.getDataMsgTypes()

        self.access = level.parser.getAccess()
        self.evict = level.parser.getEvict()

        self.archProtoGen = {}
        self.renamedMessages = level.renamedMessages
        self.hiddenChangeStates = level.hiddenChangeStates

        self.cacheStateSets = []

        self.progressMessages = level.progressMessages
        """ PROTOGEN OPTIONS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
        """
        # Options Cache
        self.CCconservativeInv = config.CCconservativeInv
        self.nonstalling = config.nonstalling

        self.maxNestingDepthCC = config.maxNestingDepthCC

        # Options Directory
        self.DCconservativeInv = config.DCconservativeInv
        self.maxNestingDepthDC = config.maxNestingDepthDC

        # Options Access Assignment
        self.stableStatesOnly = config.stableStatesOnly

        self.conservativeAccess = config.conservativeAccess
        self.ignoreDeferedStates = config.ignoreDeferedStates

        self.maxagressiveAccess = config.maxagressiveAccess

        # Options Merging
        self.enableStateMerging = config.enableStateMerging
        self.maxMergingIter = config.maxMergingIter
        self.MergeStates = MergeStates(self.maxMergingIter, self.access,
                                       self.evict)

        self._ProcessArch()
Example #4
0
 def __init__(self, debug_enable: bool = True):
     Debug.__init__(self, debug_enable)
Example #5
0
    def __init__(self,
                 parser,
                 level_id: str,
                 proto_type=None,
                 run_model_checker: bool = True,
                 debug_enabled: bool = False):

        Debug.__init__(self, debug_enabled)

        self.pheader("LEVEL: " + level_id)

        self.parser = parser
        self.level_id: str = level_id
        self.proto_type: str = proto_type
        self.state_tuple_list: List[SystemTuple] = []
        self.dir_access_classification_map = {}

        # Preprocessing make messages unique
        self.renamedMessages = {}
        self.progressMessages = []
        self.hiddenChangeStates = []

        self.model_checker = None

        # Classify communication
        CommunicationClassification().classify_parser(parser)

        self.message_objects: List[PCCObject] = parser.getMessageNodes()

        # Cache
        caches = list(parser.getCacheIdentifiers())
        assert len(
            caches
        ) <= 1, "Maximum number of architectures per parser supported is 1"
        self.cache = Architecture(parser, caches[0])

        # Cache preprocessing
        self.find_progress_messages(self.cache.state_sets)
        self.find_hidden_progess_messages(self.cache.state_sets)

        # # Make decision between memory and directory
        snoop = False
        directory = list(parser.getDirIdentifiers())
        if not directory:
            snoop = True
            directory = list(parser.getMemIdentifiers())

        assert len(
            directory
        ) <= 1, "Maximum number of architectures per parser supported is 1"
        self.directory = Architecture(parser, directory[0])

        if not snoop:
            # Detect directory message type conflicts
            self.renamedMessages.update(
                self.process_remote_requests(self.cache.state_sets,
                                             self.cache.raw_traces))
            self.cache.update_traces()

            # Resolve directory message type conflicts
            self.process_request_messages(self.renamedMessages,
                                          self.directory.state_sets)
            # Only handle silent upgrades and different request messages
            self.complete_transitions(self.cache.state_sets,
                                      self.directory.state_sets, False)

        # Update the traces
        self.cache.update_traces()
        self.directory.update_traces()

        # INITIAL MODEL CHECKING
        self.init_tuple = StateTuple(self.cache.init_state,
                                     self.directory.init_state,
                                     self.cache.init_state)
        self.level_name = "Level: " + str(level_id) + " | " + str(
            self.cache) + " && " + str(self.directory)

        if run_model_checker:
            self.initial_model_checking()

        # Complete all eviction transitions at the directory level to account for concurrency
        self.complete_transitions(self.cache.state_sets,
                                  self.directory.state_sets)
        # Update the traces
        self.cache.update_traces()
        self.directory.update_traces()

        self.cache.renamed_messages = self.renamedMessages
        self.directory.renamed_messages = self.renamedMessages

        # Classify cache and directory transitions

        # Murphi
        self.unique_id = []

        # Update machine names in operations
        self.update_mach_name_operation_append(level_id)

        self.network_class = ClassNetworkClassification(
            parser, self.cache.transitions)
Example #6
0
    def __init__(self, low_level: Level, high_level: Level, dbg_term: bool = False, dbg_graph: bool = False):

        Debug.__init__(self, dbg_term)
        self.dbg_graph = dbg_graph

        # for each ll state, add corresponding dir state and possible higher level cache states
        # higher level cache permissions are greater or equal to lower level state permissions

        # Lower level cache optimization
        # Optimization flag: Accesses that do hit in the higher level cache, do not cause the generation of
        self.ll_access_immed_hit = True

        # Higher level cache optimization
        # Optimization flag: Remote access are not conveyed to the lower level cache, if the hl trace final state has
        # lower access permissions than the current lower level caches
        self.hl_remote_immed_hit = True

        self.pessimistic_access = True

        self.complete_defer = False

        self.conservative_access_ll_request = True
        self.conservative_access_hl_request = True

        self.unique_id_str = "HIERA"
        self.unique_id = [self.unique_id_str]

        # Update messages to avoid conflicts for non-stalling implementations
        self.detect_message_dependencies(low_level, high_level)

        self.low_level: Level = copy.deepcopy(low_level)
        self.high_level: Level = copy.deepcopy(high_level)

        self.low_level.update_mach_name_operation(self.low_level.directory.get_unique_id_str(), self.unique_id_str)
        self.high_level.update_mach_name_operation(self.high_level.cache.get_unique_id_str(), self.unique_id_str)

        self.merge_data_objects()

        self.low_level.update_traces()
        self.high_level.update_traces()

        self.init_tuple: HieraStateTuple = HieraStateTuple(self.low_level.init_tuple, self.high_level.cache.init_state)

        ''' Get access mappings from lower level cache controller '''
        self.ll_access_map = access_request_mapping(self.low_level.cache.state_sets)

        self.cc_dir_to_cc_state_map: Dict[State, List[State]] = {}
        self.cc_dir_to_dir_state_map: Dict[State, List[State]] = {}

        # Do the child init here
        HieraStateSpaceGen.__init__(self, self.low_level, self.high_level)
        """ Generate State Transitions """
        HieraTransGen.__init__(self, self.low_level, self.high_level)
        HieraGraph.__init__(self, self.init_tuple, self.low_level, self.high_level)

        # Make new states based on new_state_tuples
        self.cc_dir_transitions = self.cc_dir_fsm_states()

        # Generate new stabel state nodes
        self.stable_states = self.create_cc_dir_states(self.access_state_tuples + self.remote_state_tuples +
                                                        self.ll_evict_state_tuples + self.hl_evict_state_tuples)
        if self.dbg:
            self.print_debug_info()

        # New init_state_id
        new_state_name = self.new_state_name(self.init_tuple.ll_dir_start_state.state,
                                                    self.init_tuple.hl_cc_start_state.state)

        # Make a new architecture
        self.low_level.directory = Architecture(self.low_level.directory.parser,
                                self.low_level.directory.arch_name,
                                self.cc_dir_transitions,
                                list(self.stable_states.keys()),
                                new_state_name,
                                self.unique_id,
                                self.low_level.directory.data_constant,
                                self.low_level.directory.data_object
                                )

        # Make a new architecture
        self.high_level.cache = Architecture(self.high_level.directory.parser,
                                self.high_level.cache.arch_name,
                                self.cc_dir_transitions,
                                list(self.stable_states.keys()),
                                new_state_name,
                                self.unique_id,
                                self.high_level.cache.data_constant,
                                self.high_level.cache.data_object
                                )

        self.replace_archs = [low_level.directory, high_level.cache]