KasperskyOS Community Edition 1.0

Tools for building a solution

This section contains a description of the scripts, tools, compilers and build templates provided in KasperskyOS Community Edition.

In this section

Scripts and compilers

Preparing the solution's boot image

Deploying the solution's boot image on target devices

Page top
[Topic solution_build_tools]

Scripts and compilers

This section contains a description of the scripts, tools and compilers provided in KasperskyOS Community Edition.

In this section

Build scripts and tools

Cross compilers

Page top
[Topic scripts_and_compliers]

Build scripts and tools

KasperskyOS Community Edition includes the following build scripts and tools:

  • nk-gen-c

    The NK compiler (nk-gen-c) generates the set of transport methods and types based on the EDL, CDL and IDL descriptions of applications, components and interfaces. The transport methods and types are needed for generating, sending, receiving and processing IPC messages.

  • nk-psl-gen-c

    The nk-psl-gen-c compiler generates the source code of the Kaspersky Security System security module based on the solution security policy file (security.psl) and the EDL descriptions of applications included in the solution.

  • einit

    The einit tool lets you automate the creation of code of the Einit initializing application. This application is the first to start when KasperskyOS is loaded. Then it starts the other applications and creates channels (connections) between them.

  • makekss

    The makekss script creates the Kaspersky Security System security module for the KasperskyOS kernel.

  • makeimg

    The makeimg script creates the final boot image of the KasperskyOS-based solution with all applications to be started and the Kaspersky Security System module.

In this section

nk-gen-c

nk-psl-gen-c

einit

makekss

makeimg

Page top
[Topic build_utilities_and_scripts]

nk-gen-c

The NK compiler (nk-gen-c) generates the set of transport methods and types based on the EDL, CDL and IDL descriptions of the process classes, components and interfaces. The transport methods and types are needed for generating, sending, receiving and processing IPC messages.

Transport methods and types are generated with fully qualified names. The full name of the process class/component/interface is used as prefixes in names (declared in the corresponding EDL-, CDL- or IDL file) by replacing dots with underscores (_).

The NK compiler receives the EDL, CDL or IDL file and creates the following files:

  • H file containing a declaration and implementation of transport methods and types.
  • D file that lists the dependencies of the created C file. This file can be used for building automation using the make tool.

Syntax for using the NK compiler:

nk-gen-c [-I PATH][-o PATH][--types][--interface][--client][--server][--extended-errors][--enforce-alignment-check][--help][--version] FILE

Parameters:

  • FILE

    Path to the EDL-, CDL- or IDL description of the process class, component or interface for which you need to generate transport methods and types.

  • -I PATH

    Path to the folder containing auxiliary files required for generating transport methods and types. By default, these files are located in the folder: /opt/KasperskyOS-Community-Edition-<version>/sysroot-arm-kos/include.

    It may also be used for adding other folders to search for the files required for generating the methods and types.

    To indicate more than one folder. you can use several -I switches.

  • -o PATH

    Path to an existing folder where files containing transport methods and types will be created.

  • -h, --help

    Displays the Help text.

  • --version

    Displays the nk-gen-c version.

  • --enforce-alignment-check

    Enables mandatory alignment checks for queries to memory, even if this check is disabled for the target platform. If these checks are enabled, the NK compiler adds additional alignment checks to the code of the IPC message validators.

    By default, memory query alignment check settings are defined for each platform in the file named system.platform.

  • --extended-errors

    Enables extended error handling in the code of client and server methods.

Selective generation

To reduce the amount of code generated by the NK compiler, you can use selective generation flags. For example, it is convenient to use the --server flag for applications that implement interfaces, and to use the --client flag for applications that are clients of the interfaces.

If no selective generation flag is specified, the NK compiler will create all transport types and methods that are possible for the specified file.

Selective generation flags for descriptions of interfaces (IDL files):

  • --types

    The compiler will create only files that contain all constants and types, including redefined (typedef), from the input IDL file, and the types from imported IDL files that are used in the types of the input file.

    However, constants and redefined types from imported IDL files will not be explicitly included in the generated files. If you need to use types from imported files in code, you need to separately generate H-files for each such IDL file.

  • --interface

    The compiler will generate files created with the --types flag, and the structures of request and response messages for all methods of this interface.

  • --client

    The compiler will generate files created with the --interface flag, and the client proxy objects and functions of their initialization for all methods of this interface.

  • --server

    The compiler will generate files created with the --interface flag, and the types and methods of the dispatcher of this interface.

Selective generation flags for descriptions of components (CDL files) and process classes (EDL files):

  • --types

    The compiler will generate files created with the --types flag for all interfaces used in this component/process class.

    However, only the types that are used in arguments of interface methods will be explicitly included in the generated files.

  • --interface

    The compiler will generate files created with the --types flag for this component/process class, and files generated with the --interface flag for all interfaces used in this component/process class.

  • --client

    The compiler will generate files created with the --interface flag, and the client proxy objects and functions of their initialization for all interfaces used in this component/process class.

  • --server

    The compiler will generate files created with the --interface flag, and the types and methods of the dispatcher of this component/process class and the types and methods of dispatchers for all interfaces used in this component/process class.

Page top
[Topic nkgenc]

nk-psl-gen-c

The nk-psl-gen-c compiler generates the source code of the Kaspersky Security System security module based on the solution security policy file (security.psl) and the EDL descriptions of process classes included in the solution. This code is used by the makekss script.

The nk-psl-gen-c compiler also lets you generate and run code of test scenarios written in the PAL language for the solution security policy.

Syntax for using the nk-psl-gen-c compiler:

nk-psl-gen-c [-I PATH][-o PATH][--audit PATH][--tests ARG][--help][--version] FILE

Parameters:

  • FILE

    Path to the PSL description of the solution security policy (security.psl)

  • -I,--include-dir PATH

    Path to the folder containing auxiliary files required for generating transport methods and types. By default, these files are located in the folder: /opt/KasperskyOS-Community-Edition-<version>/sysroot-arm-kos/include.

    The nk-psl-gen-c compiler will require access to all EDL descriptions of process classes listed in the security configuration, and will require access to the CDL- or IDL descriptions of their components and interfaces. To enable the nk-psl-gen-c compiler to find these descriptions, you need to pass the paths to these descriptions using the -I switch.

    To indicate more than one folder. you can use several -I switches.

  • -o,--output PATH

    Path to the created file containing the security module code.

  • -t, --tests ARG

    Flag for controlling code generation and starting test scenarios for the solution security policy. Possible values:

    • skip – code of test scenarios is not generated. This value is used by default if the --tests flag is not indicated.
    • generate – code of test scenarios is generated but is not compiled and is not executed.
    • run – code of test scenarios is generated, compiled using the gcc compiler, and executed.
  • -a, --audit PATH

    Path to the created file containing the code of the audit decoder.

  • -h, --help

    Displays the Help text.

  • --version

    Displays the nk-psl-gen-c version.

Page top
[Topic nkpslgenc]

einit

The einit tool lets you automate the creation of code of the Einit initializing application. This application is the first to start when KasperskyOS is loaded. Then it starts the other applications and creates channels (connections) between them.

The einit tool receives the init description file (init.yaml by default) and creates a .c file containing the code of the Einit initializing application. Then the Einit application must be built using the C compiler that is provided in KasperskyOS Community Edition.

Syntax for using the einit tool:

einit -I PATH -o PATH [--help] FILE

Parameters:

  • FILE

    Path to the init.yaml file containing descriptions of process classes and connections.

  • -I PATH

    Path to the folder containing auxiliary files required for generating the initializing application. By default, these files are located in the folder: /opt/KasperskyOS-Community-Edition-<version>/sysroot-arm-kos/include.

  • -o, --out-file PATH

    Path to the created .c file containing the code of the initializing application.

  • -h, --help

    Displays the Help text.

Page top
[Topic einit_tool]

makekss

The makekss script creates the security module of Kaspersky Security System.

The script calls the nk-psl-gen-c compiler to generate the source code of the security module, then compiles the resulting code by calling the C compiler that is provided in KasperskyOS Community Edition.

The script obtains the file containing a description of the solution security policy (security.psl by default) and creates the ksm.module security module file.

Syntax for using the makekss script:

makekss --target=ARCH --module=PATH --with-nk="PATH" --with-nktype="TYPE" --with-nkflags="FLAGS" [--output="PATH"][--help][--with-cc="PATH"][--with-cflags="FLAGS"] FILE

Parameters:

  • FILE

    Path to the security configuration file (.psl).

  • --target=ARCH

    Architecture for which the build is intended.

  • --module=-lPATH

    Path to the ksm_kss library. This key is passed to the C compiler for linking to this library.

  • --with-nk=PATH

    Path to the nk-psl-gen-c compiler that will be used to generate the source code of the security module. By default, the compiler is located in /opt/KasperskyOS-Community-Edition-<version>/toolchain/bin/nk-psl-gen-c.

  • --with-nktype="TYPE"

    Indicates the type of NK compiler that will be used. To use the nk-psl-gen-c compiler, indicate the psl type.

  • --with-nkflags="FLAGS"

    Parameters used when calling the nk-psl-gen-c compiler.

    The nk-psl-gen-c compiler will require access to all EDL descriptions of process classes listed in the security configuration, and will require access to the CDL- or IDL descriptions of their components and interfaces. To enable the nk-psl-gen-c compiler to find these descriptions, you need to pass the paths to these descriptions in the --with-nkflags parameter by using the -I switch of the nk-psl-gen-c compiler.

  • --output=PATH

    Path to the created security module file.

  • --with-cc=PATH

    Path to the C compiler that will be used to build the security module. The compiler provided in KasperskyOS Community Edition is used by default.

  • --with-cflags=FLAGS

    Parameters used when calling the C compiler.

  • -h, --help

    Displays the Help text.

Page top
[Topic makekss]

makeimg

The makeimg script creates the final boot image of the KasperskyOS-based solution with all applications to be started and the Kaspersky Security System module.

The script receives a list of files, including the executable files of all applications that need to be added to ROMFS of the loaded image, and creates the following files:

  • Solution image
  • Solution image without character tables (.stripped)
  • Solution image with debug character tables (.dbg.syms)

Syntax for using the makeimg script:

makeimg --target=ARCH --sys-root=PATH --with-toolchain=PATH --ldscript=PATH --img-src=PATH --img-dst=PATH --with-init=PATH [--with-extra-asflags=FLAGS][--with-extra-ldflags=FLAGS][--help] FILES

Parameters:

  • FILES

    List of paths to files, including the executable files of all applications that need to be added to romfs.

    The security module (ksm.module) must be explicitly specified, or else it will not be included in the solution image. The Einit application does not need to be indicated because it will be automatically included in the solution image.

  • --target=ARCH

    Architecture for which the build is intended.

  • --sys-root=PATH

    Path to the root directory sysroot. By default, this directory is located in /opt/KasperskyOS-Community-Edition-<version>/sysroot-arm-kos/.

  • --with-toolchain=PATH

    Path to the set of auxiliary tools required for the solution build. By default, these tools are located in /opt/KasperskyOS-Community-Edition-<version>/toolchain/.

  • --ldscript=PATH

    Path to the linker script required for the solution build. By default, this script is located in /opt/KasperskyOS-Community-Edition-<version>/libexec/arm-kos/.

  • --img-src=PATH

    Path to the precompiled KasperskyOS kernel not containing the romfs. By default, the kernel is located in /opt/KasperskyOS-Community-Edition-<version>/libexec/arm-kos/.

  • --img-dst=PATH

    Path to the created image file.

  • --with-init=PATH

    Path to the executable file of the Einit initializing application.

  • --with-extra-asflags=FLAGS

    Additional flags for the AS Assembler.

  • --with-extra-ldflags=FLAGS

    Additional flags for the LD Linker.

  • -h, --help

    Displays the Help text.

Page top
[Topic makeimg]

Cross compilers

Properties of KasperskyOS cross compilers

The cross compilers included in KasperskyOS Community Edition support processors that have the arm architecture.

The KasperskyOS Community Edition toolchain includes the following tools for cross compilation:

  • GCC:
    • arm-kos-gcc
    • arm-kos-g++
  • Binutils:
    • AS Assembler: arm-kos-as
    • LD Linker: arm-kos-ld

In addition to standard macros, an additional macro __KOS__=1 is defined in GCC. Using this macro lets you simplify porting of the software code to KasperskyOS, and also simplifies development of platform-independent applications.

To view the list of standard macros of GCC, run the following command:

echo '' | arm-kos-gcc -dM -E -

Linker operation specifics

When building the executable file of an application, by default the linker links the following libraries in the specified order:

  1. libc – standard C library.
  2. libm – library that implements the mathematical functions of the standard C language library.
  3. libvfs_stubs – library that contains stubs of I/O functions (for example, open, socket, read, write).
  4. libkos – library consisting of two parts. The first part provides the C interface for accessing KasperskyOS kernel functions. It is available through the header files in the coresrv folder, for example: #include <coresrv/vmm/vmm_api.h>. The second part of the libkos library is a wrapper over the first part and contains additional synchronization functions: mutex, semaphore, event. Other libraries (including libc) interact with the kernel through the libkos library.
  5. libenv – client library of the subsystem for configuring the environment of applications (environmental variables, arguments of the main function, and custom configurations).
  6. libsrvtransport-u – internal library with the implementation of transport of interprocess communication between KasperskyOS kernel services.
Page top
[Topic crosscompliers]

Preparing the solution's boot image

To automate the process of preparing the solution's boot image, you need to configure a build system. You can base this system on the build system implemented in the examples.

This section describes various methods for configuring a build system to prepare a solution's boot image.

In this section

Using a Makefile template from the contents of KasperskyOS Community Edition

Using CMake from the contents of KasperskyOS Community Edition

Using your own build system

Page top
[Topic build_automation_tools]

Using a Makefile template from the contents of KasperskyOS Community Edition

To simplify the process of preparing the solution's boot image using the make build system, you can use the build.mk template from KasperskyOS Community Edition. The template file is located at the following path:

/opt/KasperskyOS-Community-Edition-<version>/common/build.mk

To prepare a make build system using the build.mk template, do the following in the Makefile build script:

  1. Specify the value of the targets variable. In the variable value, list all applications included in the solution, separating them with a space. You are not required to specify the Einit or kl.core.Core applications because they are processed separately.
  2. For each application specified in the targets variable, specify the values for the following variables:
    • <application-name>-objects – list of object files of the application. You must list all object files.

      The names of object files are taken from the names of the entity source files according to the following rules:

      • *.c → *.o
      • *.idl → *.idl.o
      • *.cdl → *.cdl.o
      • *.edl → *.edl.o
    • <application-name>-ldflags – list of flags passed to the linker. If the entity uses the virtual file system, you must pass the flags specified in the LIBVFS_REMOTE variable.
    • <application-name>-base – application load address in hexadecimal. If this variable is not specified, the address is assigned automatically. Use this variable for debugging the application.

    This same address is passed to the debugger using the following command, which can be added to the .gdbinit file:

    add-symbol-file <application-name> <application-load-address>

  3. If the ROMFS partition must contain additional files, define the value for the ROMFS-FILES variable. In the variable value, list the files while separating them with blank spaces. If you are using the virtual file system, you must pass the file specified in the VFS_ENTITY variable.
  4. Add a statement for importing the build.mk template using the following command:

    include /opt/KasperskyOS-Community-Edition-<version>/common/build.mk

The build.mk template file has the following build targets:

  • sim (default target) – start the solution's boot image using the QEMU emulator.

    When started, the QEMU emulator may capture the mouse and will indicate this in the title bar of the emulator window.

  • Kos-image – build the solution's boot image to be started on the target hardware platform.
  • gdbsim – start the solution's boot image with the capability for debugging. After QEMU emulation is started, it awaits the start of the debugger. For this, call the gdb target in a different command line.

    Make sure that TCP/IP port 1234 is open by using the netstat -anput command, for example.

    Port 1234 is monitored by the gdbserver program, which is used for remote debugging of applications and is part of the QEMU emulator.

    When using the gdb debugger, you must use hardware breakpoints (hbreak). The QEMU emulator used in the examples is started with the -enable-kvm key, which makes it impossible to use regular breakpoints.

  • gdb – start the debugger. After starting the debugger for applications that require debugging, run the following commands:

    add-symbol-file <application-name> <application-load-address>

    target remote localhost:1234

Example

This example uses the make build system. In addition to the actions executed in the build.mk template, in the build script you must specify the Hello application and the list of object files of this application. The load address is specified for solution debugging purposes.

Makefile

# List of applications for the build.

targets = hello

# List of object files of the Hello application

hello-objects = hello.o hello.edl.o

# Load address of the Hello entity (in hex)

hello-base = 800000

# Include template with general build rules.

include ../common/build.mk

To start the make build system, run the make hello command.

To run the hello example while in the folder /opt/KasperskyOS-Community-Edition-<version>/examples/hello, run the make command.

Page top
[Topic using_makefiles]

Using CMake from the contents of KasperskyOS Community Edition

The CMake build automation system supports cross compilation of applications. To perform cross compilation using CMake, specify the path to a file with the build system extension (toolchain.cmake).

To cross compile an application for KasperskyOS, define the value of the variable: DCMAKE_TOOLCHAIN_FILE=/opt/KasperskyOS-Community-Edition-<version>/toolchain/share/toolchain.cmake

KasperskyOS Community Edition includes the platform library containing a set of ready-to-use scripts for the CMake system.

To prepare an application for debugging:

  1. In the CMakeLists.txt file, define the LINK_FLAGS parameter value for the application that you want to debug as follows:

    set_target_properties (<application-name> PROPERTIES LINK_FLAGS "-Ttext <text-section-address>")

    The script automatically creates .gdbinit files. The set of commands for the GDB debugger are contained within .gdbinit files. This set of commands determines which address the GDB debugger will use to load entities for debugging.

  2. Build the application.
Page top
[Topic using_cmake]

Using your own build system

You can use other build systems or implement your own build system to prepare the solution's boot image.

To prepare the solution's boot image, the build system must include the following actions:

  1. Generate code of the transport methods and types used to create, send, receive and process IPC messages between entities that are included in the solution.

    Use the NK compiler for this purpose. In command arguments, relay the path to the files containing EDL-, CDL- and IDL descriptions of entities, components and interfaces.

  2. Build all entities included in the solution.

    To do so, use the cross compilers that are included in KasperskyOS Community Edition.

  3. Build an Einit initializing entity.

    Use the einit tool to generate the code of the Einit entity. In the command arguments, pass the path to the init description file (init.yaml by default).

    Then the Einit entity must be built using the C compiler that is provided in KasperskyOS Community Edition.

  4. Build the kernel module with Kaspersky Security System.

    To do so, use the makekss script. In the command arguments, relay the path to the security configuration file (security.psl by default).

  5. Create an image of the solution.

    To do so, use the makeimg script. In the command arguments, pass the executable ELF files of entities, the kernel module with Kaspersky Security System, the KasperskyOS kernel image, and any additional files.

Page top
[Topic using_custom_build_tools]

Deploying the solution's boot image on target devices

To deploy the solution's boot image on the target device:

  1. Connect the data storage drive from which you plan to run the solution's boot image on target devices.
  2. Find the block device corresponding to the connected drive, for example, by using the following command:

    fdisk -l

  3. If required, on the storage drive, create a new partition on which the solution's boot image will be deployed by using the fdisk tool, for example.
  4. If there is no file system on the partition, create one by using the mkfs tool, for example.

    You can use any file system that is supported by the GRUB 2 bootloader.

  5. Mount the data drive.

    mkdir /mnt/kos_device && mount /dev/sdXY /mnt/kos_device

    Here, /mnt/kos_device is the mount point, /dev/sdXY is the block device name, X is the letter corresponding to the connected drive, and Y is the partition number.

  6. Install the GRUB 2 operating system bootloader on the drive.

    To install GRUB 2, run the following command:

    grub-install --force --removable \
    --boot-directory=/mnt/kos_device/boot /dev/sdX

    Here, /mnt/kos_device is the mount point, /dev/sdX is the block device name, and X is the letter corresponding to the connected drive.

  7. Copy the boot image of the solution to the root directory of the mounted drive.
  8. In the /mnt/kos_device/boot/grub/grub.cfg file, add the menuentry section that points to the solution's boot image.

    menuentry "KasperskyOS" {

    multiboot /my_kasperskyos.img

    boot

    }

  9. Unmount the drive.

    umount /mnt/kos_device

    Here, /mnt/kos_device is the mount point.

After performing these actions, you can start KasperskyOS from this drive.

Page top
[Topic deploying_solution_image]