This API is defined in the header file sysroot-*-kos/include/component/execution_manager/i_application_control.h from the KasperskyOS SDK.
The API lets you start a process from an executable file and stop this process.
Information about API functions is provided in the table below.
To start the process, call the StartEntity() function. Using the info input parameter, this function accepts process startup parameters in the StartEntityInfo structure. All fields of this structure are optional for initialization. Using the resInfo output parameter, this function returns the link to the StartEntityResultInfo structure containing the process startup results.
struct IApplicationController
{
struct StartEntityInfo
{
// Process name.Unless otherwise specified, the process class name will be used.
// If the process class name is not specified, the executable file name will be used.
std::string entityName{};
// Process class. Unless otherwise specified, the process name will be used.
// If the process name is not specified, the executable file name will be used.
std::string eiid{};
// Command-line arguments.
std::vector<std::string> args{};
// Environment variables that are passed to the started process.
std::vector<std::string> envs{};
// Environment variables that are passed to the isolated data storage of the process.
std::vector<std::string> containerEnvs{};
// Flag that defines the behavior of the Execution Manager when the process starts:
// true – pause execution and wait for the kEmAppReady event from the
// started process, which confirms its readiness to work.
// false – continue working immediately after starting the process
// without waiting for confirmation of its readiness.
bool wait{false};
// Bitmask of flags that control the behavior of the isolated data storage of the process:
// 0 – create a copy of the storage for the started process.
// EM_FLAG_DO_NOT_COPY_CONTAINER – use the storage of the parent process
// instead of creating a new copy.
uint32_t flags{0};
// Policy for handling abnormal termination of the process:
// CrashMode ::None – do not perform any action.
// CrashMode ::Dump – create a crash dump.
// CrashMode ::Panic – shut down or restart the hardware platform.
CrashMode mode{CrashMode::None};
};
struct StartEntityResultInfo
{
// Security class assigned to the process.
std::string eiid;
// Handle that identifies the started process.
EntityId entId{nk_handle_desc(INVALID_HANDLE)};
// Security ID of the started process.
Uid sid{0};
// Name of the started process.
std::string taskName;
};
};
If the mode field of the StartEntityInfo structure is set to Dump, a crash dump is automatically generated using the DumpCollector system program whenever the process crashes. The DumpCollector system program must be included in the developed KasperskyOS-based solution. (For more details on the crash dump mechanism, see Dump_collector example.) A crash dump contains diagnostic data, which includes a stack trace, the state of processor registers, thread information, and a process memory map. The generated crash dump is printed to the console using the LogRR component.
To start a process and pass a list of custom handles to it, call the StartEntityWithUserHandlesEx() function. This function receives the userHandles vector as an input parameter. This vector contains a list of custom handles that are passed to the process when it is started. Vector elements are UserHandleItem structures, which consist of a handle and its name. After a process is started, the handles transferred to this process can be found by using the KosTaskLookupResource() function based on the names of these handles.
struct UserHandleItem
{
// Handle name.
std::string id;
// Handle.
IpcHandle handle;
};
The StartEntityWithUserHandles() function starts a process and passes a list of handles to it. The list of handles is defined in the userHandles parameter, which is an array of the UserHandlesArray type:
using UserHandlesArray = std::array<nk_handle_desc_t, EM_USER_HANDLES_MAX>;
To stop a process, call the ShutdownEntity() or StopEntity() function. The entId input parameter is used by these functions to receive the handle that identifies the started process.
i_application_control.h functions
Function |
Information about the function |
|---|---|
|
Purpose Resumes a process. Parameters
Returned values If successful, the function returns |
|
Purpose Starts a process a passes the list of handles to it. The names of the handles are generated automatically. Parameters
Returned values If successful, the function returns |
|
Purpose Starts a process a passes the list of handles to it. The names of the handles can be defined by the user. Parameters
Returned values If successful, the function returns |
|
Purpose Sends a termination signal to a process. Parameters
Returned values If successful, the function returns |
|
Purpose Immediately stops the execution of a process. Parameters
Returned values If successful, the function returns |
Example of starting and stopping a process by using the StartEntity() and StopEntity() functions:
client.cpp
int main(int argc, const char *argv[])
{
// ...
const fs::path appPath{"/application"};
execmgr::IApplicationController::StartEntityResultInfo result;
execmgr::IApplicationController::StartEntityInfo info;
info.entityName = std::string{"application.Application"};
info.eiid = std::string{"application.Application"};
info.args = std::vector<std::string>{"1", "ARG1", "ARG2" , "ARG3"};
info.envs = std::vector<std::string>{"ENV1=10", "ENV2=envStr"};
std::cout << "Starting application from elf\n";
// Starting a process
if (ac->StartEntity(appPath, info, result) != kos::Ok)
{
std::cerr << "Cannot start application from " << appPath << std::endl;
return EXIT_FAILURE;
}
std::cout << "Application started with process sid " << result.sid << "\n";
auto AppId = result.entId;
// Stopping a process
if (ac->StopEntity(AppId) != kos::Ok)
{
std::cerr << "Cannot stop process " << appPath << std::endl;
return EXIT_FAILURE;
}
// ...
}
Example of starting a process and passing a custom handle to it by using the StartEntityWithUserHandlesEx() function:
client.cpp
int main(int argc, const char *argv[])
{
// ...
const fs::path appPath{"/application"};
execmgr::IApplicationController::StartEntityResultInfo result;
execmgr::IApplicationController::StartEntityInfo info;
info.entityName = std::string{"application.Application"};
info.eiid = std::string{"application.Application"};
info.args = std::vector<std::string>{"1", "ARG1", "ARG2" , "ARG3"};
info.envs = std::vector<std::string>{"ENV1=10", "ENV2=envStr"};
std::cout << "Starting application from elf\n";
// Starting a process and passing a custom handle to it
if (ac->StartEntityWithUserHandlesEx(
appPath,
info,
{
{
.id = "vfs",
.handle = nk_handle_desc(file, OCAP_FILEOP_READ | OCAP_FILEOP_WRITE | OCAP_FILEOP_STAT | OCAP_FILEOP_CLOSE | OCAP_HANDLE_TRANSFER),
},
},
result) != kos::Ok)
{
std::cerr << "Can not start entity from " << appPath << std::endl;
return EXIT_FAILURE;
}
// ...
}
application.cpp
int main(int argc, const char *argv[])
{
std::cout << "application" << " started\n";
// Verify that the custom handle was received
auto h = KosTaskLookupResource("vfs");
if (h == INVALID_HANDLE)
{
std::cout << "Cannot receive vfs handle" << std::endl;
return EXIT_FAILURE;
}
// ...
}
Page top