Understanding SST

Note

Information in this entire section has been adapted from: Ziqi Wang, “Understanding Memory Hierarchy Simulation in SST”

SST is used to simulate the memory hierarchy in SimEng. Since the entire simulation runs inside SST, SimEng needs to interact (send and recieve requests) with the memory hierarchy inside SST through an interface. The rest is handled by SST. To make sure the desired behaviour is achieved, SST needs to be appropriately configured. The SST simulation is configured using a config.py python file, which contains all components and connections between them.

Main Classes

This section only provides a brief overview of classes in the SST-Core API which are fundamental to running a simulation in SST. For more information regarding the SST-Core API please check the official SST-Core API documentation.

SST::Component

SST Component is a class in SST which represents any entity that takes in a clock from SST and performs an action on every clock tick. It is the main object for simulation and all models inherit from SST Component. Each component inside SST has to be registered with SST-Core. To find information about any component, the sst-info command can be used to display details such as configuration options, ports, etc. The output of the sst-info command can be filtered using the --libs flag.

Note

All SST components can be instantiated and configured via the use of a config.py file.

SST::SubComponent

SubComponent is a class loadable through the SST::Factory class which allows dynamic functionality to be added to a Component. The SubComponent API is nearly identical to the Component API and all the calls are forwarded to the parent Component. SubComponents are always attached to Components via slots and communicate with the component via the same.

SST Memory Model

SST Memory Model

This section describes details about components that are fundamental to the SST memory model and required for configuring a SST simulation. Each of the components mentioned here has configuration parameters which need to be specified in order for the SimEng SST simulation to work.

Note

Some configuration parameters, ports and subcomponent slots necessary for understanding the memory model are not mentioned in this section. More information about configuration parameters and connecting components through ports and subcomponents slots will be provided in Running SimEng with SST.

SimEng Core

For the SST simulation, the actual SimEng core is instantiated in a wrapper class and registered as a custom SST component, so it can receive clock ticks from SST. This component is called SimengCore.

StandardMem

StandardMem is an interface defined in SST-Core present at the namespace SST::Interfaces::StandardMem. This interface acts as an entry point between the SimEng core and SST’s memory model. Memory requests are generated by the SimEng core in the form of class  SST::Interfaces::StandardMem::Request objects, and then given to the interface class via function calls. The interface class then translates the memory requests into memory event objects that are internally used by the memory hierarchy. When a response event is received from the SST memory model, the interface class finds the matching request object, generates a response object of class SST::Interfaces::StandardMem::Response and returns it to the SimEng core via a callback function.

StandardInterface

StandardInterface is a subcomponent which implements the StandardMem interface. It is present in the memHierarchy module and needs to be configured before the simulation starts. StandardInterface is instantiated as a subcomponent of the SimEng core. SimengCore uses StandardInterface for communicating memory requests. The StandardInterface component communicates with the SimEng core using the port port. The same port is used to communicate with the highest-level component in the memory hierarchy. Communication with memory components can also be established using the subcomponent slot cpulink. Configuration details about StandardInterface can be found using the command: sst-info memHierarchy.standardInterface

Cache

Because of its size and complexity, the implementation of Cache simulation in SST is divided over multiple files. However, the CacheController class is the main contact during simulation. The CacheController class is aliased as Cache in SST. Caches in SST communicate through ports low_network_0 and high_network_0. The high_network_0 port is used to connect to either the SimEng core (via StandardMem interface) or to higher levels of cache, whereas the low_network_0 port is used to connect to lower levels of cache or the main memory of the SST memory model.

The Cache component also has some subcomponent slots (memlink and cpulink) which can be used instead of ports to establish communication as well.

Information about different configuration parameters, ports and subcomponent slots required for simulation can be found using the command: sst-info memHierarchy.Cache

MemoryController

The MemoryController class implements the memory controller interface. The memory controller object sits between the last level cache and the memory backend and it serves as an entry point for accessing the main memory. It is a SubComponent slot called backendConverter which stores a reference to the backend convertor object that is responsible for translating between memory hierarchy’s event type and the backend’s event type. The memory controller object is derived from the Component class, meaning that it can be instantiated in the configuration file, and connected to the upper-level components. All memory requests to the main memory (e.g RAM) go through the MemoryController.

The controller object also serves as an upper-level container for other memory-related components. These related components are loaded into subcomponent slots. Its backend slot stores a reference to the memory backend that implements the timing of the main memory. Its cpulink slot stores a reference to the memory link object (either a direct link or a network-on-chip endpoint) that the controller uses to communicate with upper-level components in the memory hierarchy. However, instead of using the cpulink slot, the controller can also communicate with higher memory components through the direct_link port. In addition, the backendConvertor slot stores a reference to a memory backend convertor object which is responsible for converting memory events coming from the cache hierarchy to requests used by the memory backend.

Information about the different configuration parameters, ports and subcomponent slots required for simulation can be found using the command: sst-info memHierarchy.MemController

MemoryBackend

The memory backend implements the timing model of the main memory. All memory backend implementations must inherit from the base abstract class MemBackend present in the file memBackend.h in the SST-Elements source code. Class MemBackend is an abstract class and hence cannot be directly instantiated. The abstract class inherits the SubComponent class and must be loaded into the slot of the memory controller, as we have already discussed above.

All memory backend models defined in SST inherit one of the three abstract classes i.e SimpleMemBackend, FlagMemBackend and ExtMemBackend; All these abstract classes inherit the MemBackend abstract class and require a different kind of memory backend convertor. SimpleMemBackend requires a SimpleMemoryBackendConvertor specified as memHierarchy.simpleMemBackendConvertor, FlagMemBackend requires a FlagMemBackendConvertor specified as memHierarchy.flagMemBackendConvertor and ExtMemBackend requires a ExtMemBackendConvertor specified as memHierarchy.extMemBackendConvertor.

Most of the memory timing models present inside SST inherit the SimpleMemBackend abstract class and SST provides a variety of memory backends to choose from e.g. memHierarchy.simpleMem, memHierarchy.simpleDRAM, etc.

By default the MemoryController equips the backend SubComponent slot with memHierarchy.simpleMem and backendConvertor SubComponent slot with memHierarchy.simpleMemBackendConvertor. Different memory backends and backend memory convertors can be specified in the configuration params for MemoryController.

The memory backend is the last level in the memory hierarchy and does not need to connect to any component further down.