Skip to content

Commit

Permalink
Merge pull request #389 from hermit-os/nemo
Browse files Browse the repository at this point in the history
assume that the hermit environment is already part of the OCI image
  • Loading branch information
stlankes authored Oct 8, 2024
2 parents 19ce48b + b3a79b6 commit 2964c41
Show file tree
Hide file tree
Showing 5 changed files with 15 additions and 108 deletions.
8 changes: 1 addition & 7 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -60,14 +60,8 @@ jobs:
sudo crictl version
- name: Pull images
run: |
docker pull ghcr.io/hermit-os/hermit_env:latest
docker pull ghcr.io/hermit-os/rusty_demo:latest
sudo crictl pull ghcr.io/hermit-os/rusty_demo:latest
- name: Setup Hermit environment
run: |
docker export $(docker create ghcr.io/hermit-os/hermit_env:latest) > hermit-env.tar
sudo mkdir -p /run/runh/hermit
sudo tar -xf hermit-env.tar -C /run/runh/hermit
- name: Setup rootfs
run: |
docker export $(docker create ghcr.io/hermit-os/rusty_demo:latest) > runh-image.tar
Expand All @@ -93,7 +87,7 @@ jobs:
- name: Setup runh with Docker
shell: sudo bash --noprofile --norc -eo pipefail {0}
run: |
sed -i 's/{/{ "default-runtime": "runc", "runtimes": { "runh": { "path": "\/home\/runner\/.cargo\/bin\/runh", "runtimeArgs": ["-l", "debug", "--hermit-env", "\/run\/runh\/hermit"] } },/g' /etc/docker/daemon.json
sed -i 's/{/{ "default-runtime": "runc", "runtimes": { "runh": { "path": "\/home\/runner\/.cargo\/bin\/runh", "runtimeArgs": ["-l", "debug"] } },/g' /etc/docker/daemon.json
>&2 cat /etc/docker/daemon.json
systemctl restart docker || systemctl status docker
- name: Check Docker runtime
Expand Down
50 changes: 12 additions & 38 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,49 +1,23 @@
# runh

`run` is a CLI tool for spawning and running RustyHermit containers.
To start RustyHermit application within a isolated lightweight virtual machine, a directory with the application and the loader must be created.
In this example, the binaries will be downloaded from a docker registry.
`runh` is a CLI tool for spawning and running HermitOS containers.
To start HermitOS application within a isolated lightweight virtual machine, a container registry with the the HermitOS application and its loader.

At first, the required tools will be downloaded and installed to run RustyHermit images.
To create a container image with the httpd example from the [HermitOS](https://github.com/hermit-os/hermit-rs) repository, the following `Dockerfile` is used.
The example assumes, that `httpd` and `hermit-loader-x86_64` is already created and copied to the directory, which contains the `Dockerfile`.

```sh
$ docker export $(docker create ghcr.io/hermit-os/hermit_env:latest) > hermit-env.tar
$ sudo mkdir -p /run/runh/hermit
$ sudo tar -xf hermit-env.tar -C /run/runh/hermit
```

Afterwards, the RustyHermit application will be download and store in a local directory.

```sh
$ docker export $(docker create ghcr.io/hermit-os/rusty_demo:latest) > runh-image.tar
$ mkdir -p ./runh-image/rootfs
$ tar -xf runh-image.tar -C ./runh-image/rootfs
```

In this case, the application an the loader is stored in the subdirectory `runh-image/rootfs`.

```sh
$ ls ./runh-image/rootfs
drwxr-xr-x 1 stefan stefan 128 May 24 12:27 .
drwxr-xr-x 1 stefan stefan 96 May 24 12:27 ..
-rwxr-xr-x 1 stefan stefan 3651080 May 20 13:53 rusty_demo
-rwxr-xr-x 1 stefan stefan 2225868 May 19 22:50 hermit-loader
```

An OCI specification file is required to start the hypervisor within an isolated environment.
The following commands generate a starter bundle for `rusty_demo`, create and start the container:

```sh
$ cd runh-image
$ sudo runh --root /run/runh spec --bundle . --args /hermit/rusty_demo
$ sudo runh --root /run/runh -l debug create --bundle . runh-container
$ sudo runh --root /run/runh -l debug start runh-container
```Dockerfile
FROM ghcr.io/hermit-os/hermit_env:latest
COPY hermit-loader-x86_64 hermit/hermit-loader
COPY httpd hermit/httpd
CMD ["/hermit/httpd"]
```

After a successfull test, the container can be deleted with following command:
Afterwards, the container image can be created and pushed to the registry.
The registery tag has to replace with the enduser registry.

```sh
$ sudo runh --root /run/runh -l debug delete runh-container
$ docker buildx build --tag ghcr.io/hermit-os/httpd:latest --push .
```

## Funding
Expand Down
35 changes: 1 addition & 34 deletions src/create.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
use crate::hermit;
use crate::logging::LogLevel;
use crate::mounts;
use crate::rootfs;
use crate::state;
use command_fds::{CommandFdExt, FdMapping};
Expand Down Expand Up @@ -30,7 +29,6 @@ pub fn create_container(
bundle: PathBuf,
pidfile: Option<PathBuf>,
console_socket: Option<PathBuf>,
hermit_env: Option<PathBuf>,
debug_config: bool,
child_log_level: LogLevel,
) {
Expand Down Expand Up @@ -109,8 +107,6 @@ pub fn create_container(
};
if is_hermit_container {
info!("Detected RustyHermit executable. Creating container in hermit mode!");
//Setup hermit environment
hermit::prepare_environment(&project_dir, &hermit_env);
}

//Setup exec fifo
Expand Down Expand Up @@ -170,36 +166,7 @@ pub fn create_container(
});

//Setup file system
let rootfs_path_abs = if is_hermit_container {
let overlay_root = container_dir.join("rootfs");
let overlay_workdir = overlay_root.join("work");
let overlay_upperdir = overlay_root.join("diff");
let overlay_mergeddir = overlay_root.join("merged");
mounts::create_all_dirs(&overlay_workdir);
mounts::create_all_dirs(&overlay_upperdir);
mounts::create_all_dirs(&overlay_mergeddir);
let datastr = format!(
"lowerdir={}:{},upperdir={},workdir={}",
hermit::get_environment_path(&project_dir, &hermit_env)
.as_os_str()
.to_str()
.unwrap(),
bundle_rootfs_path_abs.as_os_str().to_str().unwrap(),
overlay_upperdir.as_os_str().to_str().unwrap(),
overlay_workdir.as_os_str().to_str().unwrap()
);
nix::mount::mount::<str, PathBuf, str, str>(
Some("overlay"),
&overlay_mergeddir,
Some("overlay"),
nix::mount::MsFlags::empty(),
Some(datastr.as_str()),
)
.unwrap_or_else(|err| panic!("Could not create overlay-fs at {:?}: {}", overlay_root, err));
Cow::from(overlay_mergeddir.canonicalize().unwrap())
} else {
Cow::from(&bundle_rootfs_path_abs)
};
let rootfs_path_abs = Cow::from(&bundle_rootfs_path_abs);

//Pass spec file
let mut config = bundle;
Expand Down
25 changes: 1 addition & 24 deletions src/hermit.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
use crate::network;
use goblin::elf;
use goblin::elf64::header::EI_OSABI;
use std::{fs, path::Path, path::PathBuf};
use std::{fs, path::Path};

pub fn is_hermit_app(path: &Path) -> bool {
let buffer = fs::read(path)
Expand All @@ -14,29 +14,6 @@ pub fn is_hermit_app(path: &Path) -> bool {
}
}

pub fn create_environment(_path: &Path) {
//TODO
}

pub fn get_environment_path(project_dir: &Path, hermit_env_path: &Option<PathBuf>) -> PathBuf {
match hermit_env_path {
Some(s) => s.clone(),
None => project_dir.join("hermit"),
}
}

pub fn prepare_environment(project_dir: &Path, hermit_env_path: &Option<PathBuf>) {
let environment_path = get_environment_path(project_dir, hermit_env_path);
if !environment_path.exists() {
create_environment(&environment_path);
} else if !environment_path.is_dir() {
panic!(
"Environment path at {:?} exists but is not a directory!",
&environment_path
);
}
}

pub enum NetworkConfig {
TapNetwork(network::VirtioNetworkConfig),
UserNetwork(u16),
Expand Down
5 changes: 0 additions & 5 deletions src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,6 @@ fn parse_matches(cli: &Cli) {
bundle.clone(),
pid_file.clone(),
console_socket.clone(),
cli.hermit_env.clone(),
cli.debug_config,
cli.log_level,
),
Expand Down Expand Up @@ -213,10 +212,6 @@ struct Cli {
#[arg(long, default_value_t, value_enum)]
log_format: LogFormat,

/// Path to the hermit-environment. Defaults to <runh-root-dir>/hermit
#[arg(long, value_name = "HERMIT_ENV_PATH")]
hermit_env: Option<PathBuf>,

/// Write out any logs to the runh root directory in addition to the specified log path.
#[arg(long, default_value_t)]
debug_log: bool,
Expand Down

0 comments on commit 2964c41

Please sign in to comment.