Profiles
The Virtual Client defines the work/operations that will happen on a system in structured JSON documents called "profiles". Profiles can be thought of as recipes for how to utilize resources and to work the system. Profiles are divided into different sections within a profile including Metadata, Parameters, Actions, Monitors and Dependencies.
Although a profile may contain any number of these sections, none of the sections are absolutely required. This allows users flexibility when creating profiles for reusability. For example, it is common for the Virtual Client team to have profiles specific to running workloads on the system separat from profiles specific to running monitors on the system. This allows a user to run a set of monitors with any number of different sets of workloads. In the examples below, the profiles that start with the term 'PERF' are ones that are designed to run workloads on the system. Profiles that start with the term 'MONITORS' are designed to run different sets of monitors on the system in the background while the workloads are running.
VirtualClient.exe --profile=PERF-CPU-COREMARK.json --profile=MONITORS-DEFAULT.json ...
VirtualClient.exe --profile=PERF-CPU-OPENSSL.json --profile=MONITORS-DEFAULT.json ...
VirtualClient.exe --profile=PERF-IO-FIO.json --profile=MONITORS-DEFAULT.json ...
Metadata
The section 'Metadata' within the profile defines supplemental or context information on the purpose of the profile, general recommendations and designations for supported OS platforms and CPU architectures. Metadata is generally meant to serve as informational only and do not affect the operations of the Virtual Client with regards to the profile. There are a few metadata instructions however that do affect the operations at runtime. The following table describes some of the common metadata properties that one might find in a profile.
Metadata Property | Description | Default Value |
---|---|---|
SupportsIterations | Optional. True/False. This metadata property DOES affect the operations of the Virtual Client. When set to false, it indicates that the profile does not support profile iterations (i.e. --iterations on the command line). | |
RecommendedMinimumExecutionTime | Optional. Provides a recommendation for the minimum length of time for running the profile. This time is typically based on the amount of time expected to execute all actions in the profile 1 full round. Actions are generally executed in sequential order. Note that this is an estimate based on empirical evidence, but it is always a good idea to leave a little extra time buffer. | |
SupportedPlatforms | Optional. Defines a set of OS platforms and CPU architectures on which the profile (and all components within) is confirmed to run correctly (e.g. win-x64 -> Windows OS, X64 architecture). | |
SupportedOperatingSystems | Optional. Defines a set of operating systems on which the profile is confirmed to run correctly (e.g. Ubuntu, CentOS, Windows). This list does not indicate that the Virtual Client will run on every version of these operating systems. Focus on latest versions of the operating systems for support. |
Parameters
The section 'Parameters' within the profile defines a set of 1 or more parameters (typically with default values) that can be used to override the default values in the components that are part of the 'Actions', 'Monitors' or 'Dependencies' sections. In general, Virtual Client profiles are not meant to be overly general purpose. They represent tested and vetted recipes for how to utilize resources and work a given system. Whereas any number of parameters can be defined in the 'Parameters' section, it is common practice to allow overrides to a minimum set. This helps to ensure the purpose and consistency of the profile operations on the system cannnot diverge too far from the original intentions.
"Parameters": {
"CompilerName": "gcc",
"CompilerVersion": "10",
"ThreadCount": null
},
"Actions": [
{
"Type": "CoreMarkProExecutor",
"Parameters": {
"Scenario": "CoreMarkProBenchmark",
"PackageName": "coremarkpro"
}
}
]
Well-Known Parameters
There are certain parameters that can be used in a profile that represent aspects of the system that differ from one to another. These parameters are used to allow designers of profiles to be as expressive as possible with intentions. One of the express goals of the Virtual Client team with regards to profile design is to have profiles be as clear and self-describing as possible. It helps users to establish context into the purpose of the profile and what it will do when running on the system. The following table describes the set of well-known parameters that can be used in profiles.
Parameter | Description |
---|---|
LogicalCoreCount | Represents the number of logical cores/vCPUs on the system. |
PhysicalCoreCount | Represents the number of physical cores on the system. |
PackagePath:{package_name} | Represents the path to a package that is installed on the system by one of the dependency components (e.g. {PackagePath:openssl} ...resolving to /home/users/virtualclient/packages/openssl). |
PackagePath/Platform:{package_name} | Represents the "platform-specific" path to a package that is installed on the system by one of the dependency components. Platform-specific paths are a Virtual Client concept. They represent paths within a given package that contain toolsets and scripts for different OS platforms and CPU architectures (e.g. {PackagePath/Platform:openssl} ...resolving to /home/users/virtualclient/packages/openssl/linux-x64, /home/users/virtualclient/packages/openssl/win-arm64). |
Platform | Represents the platform-architecture for the system on which Virtual Client is running (e.g. linux-arm64, linux-x64, win-arm64, win-x64) |
ScriptPath:{script_folder} | Represents the path to a script that is copied to the build output 'scripts' directory. |
SystemMemoryBytes | Represents the total memory/RAM (in bytes) on the system. |
SystemMemoryKilobytes | Represents the total memory/RAM (in kilobytes) on the system. Note that industry standard memory unit definitions are used (e.g. 1 kilobyte = 1024 bytes). |
SystemMemoryMegabytes | Represents the total memory/RAM (in megabytes) on the system. Note that industry standard memory unit definitions are used (e.g. 1 megabyte = 1024 kilobytes or 1024 x 1024 bytes). |
SystemMemoryGigabytes | Represents the total memory/RAM (in gigabytes) on the system. Note that industry standard memory unit definitions are used (e.g. 1 gigabyte = 1024 megabytes or 1024 x 1024 kilobytes or 1024 x 1024 x 1024 bytes). |
"Actions": [
{
"Type": "RedisServerExecutor",
"Parameters": {
"Scenario": "Server",
"PackageName": "redis",
"CommandLine": "--protected-mode no --io-threads {ServerThreadCount} --maxmemory-policy noeviction --ignore-warnings ARM64-COW-BUG --save",
"BindToCores": true,
"Port": "$.Parameters.ServerPort",
"ServerInstances": "{LogicalCoreCount}",
"ServerThreadCount": "$.Parameters.ServerThreadCount",
"Role": "Server"
}
}
]
"Dependencies": [
{
"Type": "WgetPackageInstallation",
"Parameters": {
"Scenario": "InstallMemcachedPackage",
"PackageName": "memcached",
"PackageUri": "https://memcached.org/files/memcached-1.6.17.tar.gz",
"SubPath": "memcached-1.6.17",
"Notes": "Example path to package -> /packages/memcached/memcached-1.6.17"
}
},
{
"Type": "ExecuteCommand",
"Parameters": {
"Scenario": "CompileMemcached",
"Platforms": "linux-x64,linux-arm64",
"Command": "bash -c './configure'&&make",
"WorkingDirectory": "{PackagePath:memcached}"
}
}
]
"Dependencies": [
{
"Type": "DependencyPackageInstallation",
"Parameters": {
"Scenario": "InstallCoreMarkPackage",
"BlobContainer": "packages",
"BlobName": "coremark.1.0.0.zip",
"PackageName": "coremark",
"Extract": true
}
},
{
"Type": "ExecuteCommand",
"Parameters": {
"Scenario": "CompileCoremark",
"Platforms": "linux-x64,linux-arm64",
"Command": "bash -c './configure'&&make",
"WorkingDirectory": "{PackagePath/Platform:coremark}"
}
}
]
"Dependencies": [
{
"Type": "DependencyPackageInstallation",
"Parameters": {
"Scenario": "InstallCustomToolsetPackage",
"BlobContainer": "packages",
"BlobName": "customtoolset-{Platform}.1.0.0.zip",
"PackageName": "customtoolset-{Platform}",
"Extract": true
}
},
{
"Type": "ExecuteCommand",
"Parameters": {
"Scenario": "InstallCustomToolset",
"Platforms": "{Platform}",
"Command": "bash -c 'install-toolset.sh'",
"WorkingDirectory": "{PackagePath:customtoolset-{Platform}}"
}
}
]
"Actions": [
{
"Type": "FioExecutor",
"Parameters": {
"Scenario": "FioExecutorJobFile",
"PackageName": "fio",
"JobFile": "{ScriptPath:fio}/oltp-c.jobfile",
"CommandLine": "--thread {JobFile}"
}
}
]
"Actions": [
{
"Type": "MemcachedServerExecutor",
"Parameters": {
"Scenario": "Server",
"PackageName": "memcached",
"CommandLine": "-p {Port} -t 4 -m {ServerMemory} -c {ServerMaxConnections}",
"BindToCores": true,
"Port": "$.Parameters.ServerPort",
"Username": "$.Parameters.Username",
"ServerThreadCount": 4,
"ServerMaxConnections": "$.Parameters.ServerMaxConnections",
"ServerMemory": "{calculate({SystemMemoryMegabytes} / 2)}",
"Role": "Server"
}
}
]