The content and structure of this section is related to our work [SRNB13b] which is currently under review. A separate process runs in the background on one thread without pinning and executes the resource manager (RM). The task of the resource manager is then the optimization of the resource distribution and is based on the information provided by the applications via constraints. Such constraints can be e.g. scalability graphs, workload and range constraints, see Sec. 8.2.1. For sake of clarity, Table 8.1 gives an overview of the symbols used in this and the upcoming section.
Symbol | Description |
R | Number of system-wide available computing resources |
N | Number of concurrently running processes |
List of running applications or MPI processes |
|
ϵ | Placeholder for ”no application” |
r | State of resource assignments to applications |
i | Optimal resource distribution assigning Di cores to application Ai |
i | Optimization information (scalability graphs, e.g.) for application i |
i | Optimization targets (throughput, energy, etc.) for each application |
i | Number of resources currently assigned to application i |
i | List of free resources |
i | Workload for application i |
T(c) | Throughput for c cores |
Si(c) | Scalability graph for application i. |
The RM aims at optimizing the core-to-application assignment stored in the vector . Here, each entry represents the association of the R = || physical cores to the applications. The application id is stored to i if core i is assigned to the application. In case of no core assignment, ϵ is used as a placeholder.
Here, we describe our algorithm which optimizes the resource distribution based on the constraints provided by the applications. Again, let R be the amount of system-wide available compute resources. Further, let N be the amount of concurrently running applications, ϵ a marker for a resource not assigned to any application and a list of identifiers of concurrently running applications, with || = N. Then, we distinguish between management data inside the RM: uniquely per-application and system-wide data.
Per-application data: For each application i, there is a i storing the currently specified constraints which were previously send to the RM via a (non-)blocking invade. The RM uses these constraints for optimizations, depending on the desired optimization targets which are discussed in Section 8.4.
System-wide data: The system-wide management data is defined with the current resource assignment and an optimization target. Such optimization targets e.g. request a maximization of the application throughput or for future applications the minimization of energy consumption. Then,
We further demand
| (8.1) |
to avoid oversubscription of these resources. This avoids assignment of more resources than there are available on the system. The resource collision itself is avoided by assigning the resources via the vector . Here, each core can be assigned to only a single application. Cores which are currently assigned to an application are additionally stored in a list for releasing them without a search operation on .
A loop is used inside the RM which successively optimizes the resource distribution. Here, the resource distribution is updated based on the constraints. Further, the current resource distribution is optimized towards the optimal target resource distribution . The optimization loop can be separated into three parts:
The optimization function is executed every time if a new one is available (setup), a constraint is updated (invade) or removed (shutdown). This optimization function is given by
| (8.2) |
in its general form. Here, the vector of optimization targets is given in , e.g. targets such as throughput or load distribution. contains the application constraints and the current distribution of cores to applications is given in (i).
The computation of the target distribution with foptimize is further described in Section 8.4. Then, (i+1) contains the configuration of the computing cores to which the resource distribution has to be updated and the superscript (i) annotates the i-th execution of the optimization function.
For applications which are sensitive to non-uniform memory access (NUMA), the target core-to-application can be beneficial and is also returned in (i+1). In the current implementation, this core-to-application assignment is not used and we continue using only the quantitative optimization given in (i+1).
Given the list of applications, the resource redistribution is then optimized either by assigning additional cores or releasing cores for each application. Here,