Building ILLIXR
The ILLIXR application is kick-started through a tool called Runner
(found in runner/
and runner.sh
).
The Runner tool is responsible for
preparing the environment,
downloading required assets/code,
compiling each plugin,
and
launching the ILLIXR application.
Runner is necessary for our project since ILLIXR manages plugins and data that span
many locations and launch configurations.
A configuration (defined via a YAML file in ILLIXR/configs/
) specifies parameters
and plugins required to launch ILLIXR for a specific design/evaluation scenario.
Compilation and Usage
To run ILLIXR (from the root directory of the project) using
the default native
launch configuration,
./runner.sh configs/native.yaml
To drop into gdb
, add command: gdb -q --args $cmd
in the action
block of
configs/native.yaml
, and use the same command.
To run ILLIXR with Monado,
./runner.sh configs/monado.yaml
The OpenXR application to run is defined in the action.openxr_app
(a YAML object).
Configuration
As introduced in the introduction to the ILLIXR build process, a Configuration
(or config) describes the key information needed to launch an ILLIXR application.
This section provides a detailed breakdown of the structure of a configuration file.
The default ILLIXR/configs/native.yaml
for the native
action will be used as
the running example.
The first block in the config file contains a list of plugin_groups
,
where each plugin_group
is a list of plugins.
plugin_groups:
- plugin_group:
- path: plugin1/
- path: plugin2/
- path: plugin3/
- path: plugin4/
This defines a list of plugins by their location, path
.
Allowed paths will be described below.
The plugin_groups
get flattened and those plugins are initialized in order at runtime.
Several of the default plugins are order-sensitive.
The next block in the config defines the offline IMU data, camera data, and ground-truth data.
data:
subpath: mav0
relative_to:
archive_path:
download_url: 'http://robotics.ethz.ch/~asl-datasets/ijrr_euroc_mav_dataset/vicon_room1/V1_02_medium/V1_02_medium.zip'
Next, we define the location of OBJ files for gldemo
.
demo_data: demo_data/
Then, we define the Action to be taken for the configuration. Each action has a name, and can contain a number of member fields beyond this.
action:
name: native
command: gdb -q --args $cmd
The native
action supports an optional command
argument.
In that argument $cmd
is replaced with the separated command-line arguments to run ILLIXR,
while $quoted_cmd
is replaced with a single string comprising all command-line arguments.
The command
argument also supports $env_cmd
, which interpret command-line argument
assignments in the form of VARNAME=VALUE
as environment variable mappings.
See the configuration glossary entry for more details about supported actions.
Finally, we support two compilation profiles:
opt
, which compiles with -O3
and disables debug prints and assertions,
and
dbg
, which compiles with debug flags and enables debug prints and assertions.
profile: opt
You can !include
other configuration files via pyyaml-include.
Consider separating the site-specific configuration options into its own file.
Specifying Paths
A path refers to a location of a resource. There are 5 ways of specifying a path:
-
Simple path: Either absolute or relative path in the native filesystem.
-
Git repo: A git repository.
- git_repo: https://github.com/user/repo.git version: master # branch name, SHA-256, or tag
-
Download URL: A resource downloaded from the internet.
- download_url: https://example.com/file.txt
-
Zip archive: A path that points within the contents of a zip archive. Note that
archive_path
is itself a path (recursive).- archive_path: path/to/archive.zip - archive_path: download_url: https://example.com/file.zip
-
Complex path: A hard-coded path relative to another path (recursive). This is useful to specify a subdirectory of a git repository or zip archive.
- subpath: path/within/git_repo relative_to: git_repo: ... version: ...
Rationale
-
Previously, we would have to specify which plugins to build and which to run separately, violating DRY principle.
-
Previously, configuration had to be hard-coded into the component source code, or passed as parsed/unparsed as strings in env-vars on a per-component basis. This gives us a consistent way to deal with all configurations.
-
Currently, plugins are specified by a path to the directory containing their source code and build system.
Philosophy
-
Each plugin should not have to know or care how the others are compiled. In the future, they may even be distributed separately, just as SOs. Therefore, each plugin needs its own build system.
-
Despite this per-plugin flexibility, building the 'default' set of ILLIXR plugins should be extremely easy.
-
It should be easy to build in parallel.
-
Always rebuild every time, so the binary is always "fresh." This is a great convenience when experimenting. However, this implies that rebuilding must be fast when not much has changed.
-
Make is the de facto standard for building C/C++ programs. GNU Make, and the makefile language begets no shortage of problems [1,2,3,4,5], but we choose Make for its tradeoff of between simplicity and functionality. What it lacks in functionality (compared to CMake, Ninja, scons, Bazel, Meson) it makes up for in simplicity. It's still the build system in which it is the easiest to invoke arbitrary commands in shell and the easiest to have a
common.mk
included in each plugin. This decision to use Make should be revisited, when this project outgrows its ability, but for now, Make remains, in our judgement, the best tool for the job.