1.4 Interfaces and communication

The following diagram provides an overview of the Iris interfaces:

Figure 1-1 Iris architecture
To view this graphic, your browser must support the SVG format. Either install a browser with native support, or install an appropriate plugin such as Adobe SVG Viewer.


An Iris system consists of the following:

Simulator executable

The simulator executable can be implemented using C or C++, SystemC, Gem5, or Fast Models. It can be a standalone executable or a DSO.

Iris instances

The term Iris instance, or just instance, refers to an entity that can send and receive Iris function calls. This includes all components, plug-ins, clients, for example debuggers, and framework entities, for example the global instance. All Iris instances can send and receive Iris function calls to and from all other instances. In Figure   1-1 Iris architecture, Iris instances are shown by boxes with a bold outline.

IrisSupportLib
A static library named IrisSupport.lib or libIrisSupport.a that provides the following core Iris functionality:
  • The global instance and the global instance registry.
  • Routes all Iris messages.
  • Plug-in loading.
  • The IrisTcpServer.
It is linked and managed by the model. IrisSupportLib is documented in IrisSupportLib Reference Manual.
framework.GlobalInstance

This is the central routing instance between all Iris instances. The global instance registry records all Iris instances in the system. All Iris instances must register and unregister themselves in the instance registry, and they can use it to query a list of all other instances.

IrisTcpServer

TCP server that is provided by IrisSupportLib and runs as part of the simulator executable. It listens for connections from TCP clients, typically an IrisTcpClient. It transparently forwards function calls and responses. It does not explicitly support Iris functions, so extending the Iris interface, for example by adding functions or arguments, or adding new data structures, does not require any changes to the IrisTcpServer.

The IrisInterface communication trivially maps onto a TCP socket because it is inherently split between request and response, and because function calls and responses are data only. This data is transmitted almost unchanged over TCP between clients and servers.

IrisC API
A C interface that is used on DSO boundaries. It is equivalent to the C++ IrisInterface.
U64JSON

A proprietary binary variant of JSON, which is JSON-compatible. It is based on uint64_t arrays and is optimized for speed, not size. It removes the runtime overhead of JSON parsing and data conversion. It is used in-process and is one of many options for out-of-process, or IPC communication.

IrisInterface

An in-process, generic mechanism that transports Iris function calls, including callbacks and responses. In-process function calls and responses are made according to the JSON RPC 2.0 specification and are encoded in U64JSON. Instance implementations usually use a helper class, IrisInstance, which hides the internals of IrisC, IrisInterface, and U64JSON.

IrisInstance

Implements all necessary boilerplate code to provide debuggers and components with easy access to Iris functions. IrisSupportLib provides implementations for C++ and Python. For example, it provides:

  • Encoding and decoding of function calls.
  • Blocking function call semantics.
  • Data in native data types for the language being used.
  • Generic error messages.
IrisTcpClient

TCP client that is provided by IrisSupportLib. As with the IrisTcpServer, extending the Iris interface does not require any changes to the IrisTcpClient. Using the IrisTcpClient to connect to the IrisTcpServer is not mandatory, but is convenient. A client application, for example a debugger, typically uses an IrisInstance connected to an IrisTcpClient to connect to an Iris server running in the model process.

Iris function calls over TCP

The protocol that is used over TCP and the format and semantics of all Iris functions are defined and public. In Figure   1-1 Iris architecture, they are shown by dashed lines.

client.debugger

A C++ client application that uses IrisSupportLib, built from source. It can call Iris functions directly from C++ and can update the IrisSupportLib source at any time. An update is not mandatory after the simulator executable has updated any part of the system. Clients and simulators can update at different times. There are no shared header files, but both sides must follow the Iris specification to be compatible.

client.PythonScript

The same as client.debugger but written in Python.

component.Plugin0 and component.Plugin1

These plug-ins use IrisInstance to communicate with the rest of the system. There is no difference between a plug-in and a client that is connected using IPC in how they call and are called by Iris functions, except for the plug-in loading mechanism and speed considerations.

Note:

Plug-ins can communicate with each other in the same way as with the rest of the system, including with clients connected using IPC.
component.Comp0-2

Components written in C++, LISA, or SystemC, that model hardware or perform other simulation functionality. They use IrisInstance to avoid being exposed to the internals of the function call mechanism, and to use infrastructure that is common to a lot of components, for example meta information for registers and memory spaces. Internally in the IrisInstance, they send and receive U64JSON-encoded Iris function calls through the low-level IrisC API. They might buffer these function calls in an event queue. Later on, and typically from another thread, they send the response back to the IrisInterface of the global instance.

Transports

Iris function calls are transported using the following mechanisms:

  • In-process. The transport is the IrisC interface on DSO boundaries and the C++ IrisInterface inside DSOs. The Iris interface is bi-directional so it can send function calls and responses in both directions. IrisInterface only supports U64JSON directly, but adapters exist to enable function calls from C++ and Python directly, or to use other formats, for example JSON. The in-process mechanism is used whenever possible, typically by:

    • Plug-ins that communicate with component instances, for example to receive trace and to inspect components.
    • The global instance to communicate with component instances. For example, components register themselves with the global instance at startup.
    • The IrisTcpServer to communicate with component instances and with the global instance.
  • Inter Process Communication (IPC). The transport is a TCP socket. Usually the simulation contains a TCP server which listens for inbound connections. Iris calls and their responses are sent in both directions across the same TCP socket. The TCP connection is persistent.

    Various formats can be used across the TCP connection, including U64JSON and JSON. IPC is used only if necessary, typically by IPC clients, for example debuggers, shells, and IPC plug-ins, to communicate with component instances, the global instance, plug-ins, or even other clients.

Non-ConfidentialPDF file icon PDF version101196_0100_03_en
Copyright © 2018, 2019 Arm Limited or its affiliates. All rights reserved.