Compare commits

...

730 Commits
v0.1.0 ... main

Author SHA1 Message Date
Yariv Rachmani c9868e8507
Merge pull request #910 from containers/hostname
setup: install hostname
2025-08-10 08:14:36 +03:00
Douglas Schilling Landgraf 5938fa91fe setup: install hostname
QE scripts need hostname pkg

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-08-08 12:07:09 -04:00
Albert Esteve 3c960da3cc
oci-hooks: Refactor and test (#896)
Merge qm-oci-hooks-wayland and device
hooks to reuse the scrip file.

Add tests to the infrastructure.

Split some library files to facilitate
testing by adding some mocking functions.

Assisted-by: Cursor - claude-4-sonnet model

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2025-08-07 10:51:33 -04:00
Yariv Rachmani 1e6111f2d4
Adding verification check for flood testing (#908)
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-08-07 10:11:16 -04:00
Yariv Rachmani c84b01d598
Merge pull request #906 from containers/reducefiles
Makefile: reduce the make dist files
2025-08-07 11:24:22 +03:00
Douglas Schilling Landgraf 08fb1c1a66 Makefile: reduce the make dist files
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-08-05 21:49:20 -04:00
Douglas Landgraf d3cd2a04e4
bump release to v0.9 (#905)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-08-05 11:28:10 -04:00
Douglas Landgraf 6ad8cb5ff4
spec: remove iptables requirement (#902)
It's affecting AutoSD10.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-08-05 11:02:35 -04:00
Yariv Rachmani da31efb4d8
Merge pull request #901 from Yarboa/copr-release-fix
Complete #136
2025-08-05 16:05:37 +03:00
Yariv Rachmani 595be738b9 Complete #136
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-08-05 13:05:46 +03:00
Douglas Landgraf 257e73d65d
build_kvm_container: replace openssl to fedora (#900)
Set default password to fedora instead of dynamic pass
to generate the image.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-08-04 17:39:58 -04:00
Yariv Rachmani 8f137784f2
Update push on commit - to automotive-sig copr (#898)
resolve #136

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-08-04 10:45:17 -04:00
ArtiomDivak f0b8127906
Add qmctl subpackage to RPM spec (#895)
- Add qmctl installation to Makefile install target
- Create qm-ctl subpackage in rpm/qm.spec
- Install qmctl binary to /usr/bin/qmctl
- Install qmctl.1 manual page to /usr/share/man/man1/
- Include project README.md and LICENSE in subpackage
- Allow separate installation of qmctl command-line tool

Signed-off-by: Artiom Divak <adivak@redhat.com>
2025-07-29 09:27:09 -04:00
Albert Esteve fab260d36c
Use OCI Hooks for other devices (#889)
* oci-hooks: Add qm-device-manager

Signed-off-by: Albert Esteve <aesteve@redhat.com>

* rpm: Add qm-device-manager subpackage

Signed-off-by: Albert Esteve <aesteve@redhat.com>

* Subpackages: remove unused and update doc

Remove unused packages, and dropins. Also,
update any drop-in that may benefit from
using qm-oci-hooks and add the dependency
to the spec file.

Update docs accordingly.

Signed-off-by: Albert Esteve <aesteve@redhat.com>

* oci-hooks: Add logging for all hooks

Signed-off-by: Albert Esteve <aesteve@redhat.com>

* tests: test qm-oci-hooks

Signed-off-by: Albert Esteve <aesteve@redhat.com>

---------

Signed-off-by: Albert Esteve <aesteve@redhat.com>
Co-authored-by: Douglas Landgraf <dougsland@redhat.com>
2025-07-23 14:56:49 -04:00
Yariv Rachmani c063b36fbb
Replacing old podman copr repo (#890)
"${PACKIT_COPR_PROJECT:-rhcontainerbot/qm}"  ->
"${PACKIT_COPR_PROJECT:-rhcontainerbot/podman-next}"

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
Co-authored-by: Douglas Landgraf <dougsland@redhat.com>
2025-07-22 20:05:12 -04:00
Douglas Landgraf 034378e7c8
setup: add support to libkrun (#871)
* setup: add support to libkrun

setup is used in CI/CD, good to have such support.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

* Moved install of ROOTFS packages

ROOTFS dir is created from the host repositioies,
While bluechi and libkrun installed with their specific rpm.repo.d
That way ROOFS is mounted and other rpms could be installed without
breaking ROOTS partition

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

---------

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
Co-authored-by: Yariv Rachmani <yrachman@redhat.com>
2025-07-22 17:51:42 -04:00
Roberto Majadas 9f2801ec0f
Add OCI hooks for Wayland device configuration (#884)
- Implemented `oci-qm-wayland-session-devices` hook for managing seat-specific device access in multi-seat environments.
- Implemented `oci-qm-wayland-client-devices` hook for enabling GPU hardware acceleration for Wayland clients.
- Added documentation for configuration and usage.

Signed-off-by: Roberto Majadas <rmajadas@redhat.com>
2025-07-18 09:04:35 -04:00
Douglas Landgraf a633389b5c
bump version to 0.8 (#885)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-07-17 10:15:04 -04:00
ArtiomDivak 4efd62c237
Fix ValidationError handling to properly show error and exit (#872)
* Fix ValidationError handling to properly show error and exit

- Added QmError exception handler in run_command_with_error_handling()
- Moved validation calls inside try-except blocks for proper error handling
- Fixed exec_in_container, execin_in_container, copy_in_container, and show methods
- ValidationError now shows error message and exits cleanly instead of crashing

Signed-off-by: Artiom Divak <adivak@redhat.com>

* Fix ValidationError handling to properly show error and exit

- Added QmError exception handler in run_command_with_error_handling()
- Moved validation calls inside try-except blocks for proper error handling
- Fixed exec_in_container, execin_in_container, copy_in_container, and show methods
- ValidationError now shows error message and exits cleanly instead of crashing

Signed-off-by: Artiom Divak <adivak@redhat.com>

---------

Signed-off-by: Artiom Divak <adivak@redhat.com>
2025-07-17 09:59:30 -04:00
ArtiomDivak 13a16718bf
Issue 865 (#867)
* Added QMCTL class

This MR I added QMCTL class wich will be responsiable to run all the
command function and return the result. Also added all the imports
needed to all the file

Signed-off-by: Artiom Divak <adivak@redhat.com>

* qmctl: Add comprehensive help examples for all subcommands

Add detailed examples to qmctl help output including:
- Main help with overview examples for all commands
- Individual subcommand help with specific examples
- Examples for show, exec, execin, and cp commands
- JSON output examples for each command
- Practical usage scenarios

This improves user experience by providing clear guidance
on how to use each qmctl command effectively.

Closes https://github.com/containers/qm/issues/865

Signed-off-by: Artiom Divak <adivak@redhat.com>

---------

Signed-off-by: Artiom Divak <adivak@redhat.com>
Co-authored-by: Douglas Landgraf <dougsland@redhat.com>
2025-07-17 09:57:53 -04:00
Yariv Rachmani 70ce24df95
Update qm-2-qm ipc rules (#877)
* Update qm-2-qm ipc rules

For qm-2-qm no need to maintain connection through
qm_t systemd socket file

Signed-off-by: yarboa <yrachman@redhat.com>
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

* remove qm_var_run_t

qm_var_run_t not needed in case of qm to qm ipc
For ipc through qm_t socket, use qm_container_ipc_t type
Update ipc_client quadlet
 - dependency with ipc_server
 - client mount socket as volume

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

* Update docs/docs/ipc.md

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

---------

Signed-off-by: yarboa <yrachman@redhat.com>
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-07-17 09:33:34 -04:00
Yariv Rachmani ceebe725e6
Merge pull request #874 from aesteve-rh/limit-mqueues-max
qm.container: Limit max mqueues to 4
2025-07-17 13:16:07 +03:00
Albert Esteve bfcd6bcc20 qm.container: Limit max mqueues to 4
Limit the max number of message queues to 4.
Create a test to verify this setting.

Reasoning:
With default `msgsize_max` of `8192` and an
`ulimit` of `819200`, we can only fit up to 9
buffers simultaneously. By limiting the QM to
4 we ensure that more than half of the available
memory is kept available for the ASIL layer.

Fixes: https://github.com/containers/qm/issues/873
Signed-off-by: Albert Esteve <aesteve@redhat.com>
2025-07-16 13:40:10 +02:00
Yariv Rachmani 4d74d3aaa6
Merge pull request #860 from pengshanyu/kvm-basic-test
add a basic kvm in container test
2025-07-16 13:52:20 +03:00
Yariv Rachmani 217f23c065
Merge pull request #876 from containers/asil-to-qm
docs: ipc asil to qm
2025-07-16 13:49:29 +03:00
pengshanyu 1df8743403 add kvm test
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2025-07-16 12:48:36 +08:00
Douglas Schilling Landgraf e9e0d962bb docs: ipc asil to qm
Add example of ASIL to QM IPC env

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-07-15 20:22:48 -04:00
Daniel J Walsh a8575fc136
Merge pull request #875 from rhatdan/selinux
Limit the number of SELinux calls qm containers can do
2025-07-15 08:58:28 -04:00
Daniel J Walsh 1c0350960d
Limit the number of SELinux calls qm containers can do
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2025-07-14 12:22:15 -04:00
ArtiomDivak 85a8640c15
Restructure qmctl (#839)
* Added QMCTL class

This MR I added QMCTL class wich will be responsiable to run all the
command function and return the result. Also added all the imports
needed to all the file

Signed-off-by: Artiom Divak <adivak@redhat.com>

* Adding ArgumentParserWithDefaults and SubcommandInitializer

ArgumentParserWithDefaults class automatically adds default values to the help text of arguments
SubcommandInitializer is a generic class to initialize subparsers for command-line applications

Signed-off-by: Artiom Divak <adivak@redhat.com>

* Added the core of QMCTL

This commits adds the main function the init of the subcommand and the
handle function for the subcommand with other vital function.

Signed-off-by: Artiom Divak <adivak@redhat.com>

---------

Signed-off-by: Artiom Divak <adivak@redhat.com>
Co-authored-by: Douglas Landgraf <dougsland@redhat.com>
2025-07-10 16:31:01 -04:00
Daniel J Walsh 0bea8fa121
Merge pull request #863 from containers/specipc
qm.spec: add validation for file context entries
2025-07-10 07:52:20 -04:00
Yariv Rachmani 6dd6ec4fa4
Merge pull request #862 from aesteve-rh/krun-support
qm.if: allow process setcurrent for qm_t
2025-07-09 10:30:25 +03:00
Douglas Schilling Landgraf 19c6d30934 qm.spec: add validation for file context entries
RHEL < 10 and Fedora < 40 use file context entries in /var/run.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-07-08 14:59:29 -04:00
Albert Esteve d3e4209241 qm.if: allow process setcurrent for qm_t
Update SELinux rules to support krun
runtime to work properly inside QM
container.

Update check_libkrun.sh test accordinly.

Fixes: https://github.com/containers/qm/issues/846
Signed-off-by: Albert Esteve <aesteve@redhat.com>
2025-07-08 15:33:34 +02:00
Ian Mullins c4f1ed9cf0
Improve logging in setup script (#841)
Improve error handling and logging output.
Add more details where qm.service fails to start.

Signed-off-by: Ian Mullins <imullins@redhat.com>
2025-06-30 16:28:37 -04:00
Michael Engel 7d9bc52e5c
Move readmes to readthedoc (#856)
* Moved README content to readthedoc pages

Signed-off-by: Michael Engel <mengel@redhat.com>

* Removed non-existing and unused js reference from mkdocs.yml

Signed-off-by: Michael Engel <mengel@redhat.com>

---------

Signed-off-by: Michael Engel <mengel@redhat.com>
2025-06-30 16:28:20 -04:00
Michael Engel 5c4aa9546d
Merge pull request #853 from containers/doc-ipc
doc: IPC documentation
2025-06-30 12:29:28 +02:00
Douglas Landgraf dcd89dddbe
bump release 0.7.6 (#855)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-06-27 19:18:57 -04:00
Douglas Schilling Landgraf 72e7f5adc8 doc: IPC documentation
Explain communication between ASIL to QM and QM to QM.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-06-27 18:30:29 -04:00
Daniel J Walsh 648f6416ca
Merge pull request #850 from rhatdan/selinux
Add filetrans rule for ipc_var_run_t directory named ipc
2025-06-25 12:56:12 -04:00
Daniel J Walsh 3923c628f1
Add filetrans rule for ipc_var_run_t directory named ipc
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2025-06-24 09:35:36 -04:00
Daniel J Walsh f5c47e2bee
Merge pull request #845 from pengshanyu/libkrun-test-c9s
add QM libkrun test against c9s
2025-06-20 10:39:23 -04:00
pengshanyu 1758aab6a3 add comment
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2025-06-18 15:29:15 +08:00
pengshanyu 5e98e5826f update tag
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2025-06-17 15:56:45 +08:00
pengshanyu fb6116c5cf add libkrun c9s test
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2025-06-17 14:25:16 +08:00
Douglas Landgraf 2e70fe16d3
bump release 0.7.5 (#844)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-06-16 16:51:38 -04:00
Daniel J Walsh 9f2b3fa700
Fix file label specification (#842)
As of latest fedora and RHEL 10 the specifications should be on
/run
not on /var/run.

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2025-06-16 16:21:08 -04:00
ArtiomDivak daec692be0
Qmctl tests (#831)
Closes: https://issues.redhat.com/browse/VROOM-28614

Signed-off-by: Artiom Divak <adivak@redhat.com>
2025-06-04 08:40:28 -03:00
Ian Mullins 647e56c900
Improve subpackage CI/CD rpm build process and error handling (#836)
Add explicit RPM existence checks after builds in subsystem Makefiles to ensure successful subpackage
creation.

Signed-off-by: Ian Mullins <imullins@redhat.com>
2025-06-02 08:12:22 -03:00
pengshanyu 3ab116d733
improve deny_set_scheduler (#833)
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2025-05-21 08:44:27 -04:00
pengshanyu f4314581b1
improve deny_set_scheduler (#832)
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2025-05-20 08:49:05 -04:00
Douglas Landgraf 4fbfebc24b
manpage: man page for qmctl (#829)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-05-19 09:10:18 -04:00
Laura Marsh b4b399c927
Adding README updates (#825)
* Adding README updates

Signed-off-by: Laura Marsh <lmarsh@redhat.com>

* fixed typo qm_selinx > qm_selinux

Signed-off-by: Laura Marsh <lmarsh@redhat.com>

---------

Signed-off-by: Laura Marsh <lmarsh@redhat.com>
2025-05-12 17:08:55 -04:00
Douglas Landgraf 10c87d916d
sched_setscheduler to allow other, batch idle (#824)
The current seccomp changes completely disallow
calling sched_setscheduler, but we can safely
allow calling it with policy==SCHED_OTHER/BATCH/IDLE,
as really the only problem is the various real-time classes.

The profile argument is the second (id 1) and the values for
the classes are OTHER=0, BATCH==3, IDLE==5

Resolves: #702
See-Also: https://github.com/containers/qm/pull/818

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-05-12 10:57:09 -04:00
Alexander Larsson 2ca6668b12
Merge pull request #797 from engelmi/tighten-bluechi-agent-policy
Restrict access to the mounted socket to bluechi-agent
2025-05-07 11:38:18 +02:00
Michael Engel 4b3d2dfc61
Restrict access to the mounted socket to bluechi-agent
Signed-off-by: Michael Engel <mengel@redhat.com>
2025-05-02 14:53:28 +02:00
Ian Mullins 0f170e8967
Docs: Custom subpackage creation (#821)
Develop documentation on how to create custom subpackages.
Move subpackage section from the main developers guide to experimental.

Signed-off-by: Ian Mullins <imullins@redhat.com>
2025-05-01 14:49:23 -04:00
michalskrivanek 45f3e6e569
a-i-b.sh moved from sample-images to a-i-b (#820)
update where to get the script from

Signed-off-by: Michal Skrivanek <michal.skrivanek@redhat.com>
2025-05-01 14:47:04 -04:00
Ian Mullins 4eba902d46
Fixes for broken subpackages (#822)
- Fix subpackages currently failing to build
- Also address subpackage naming consistency

Signed-off-by: Ian Mullins <imullins@redhat.com>
2025-05-01 14:45:27 -04:00
Ilia Markelov 8b53cea2ae
ttyUSB0 test manual (#819)
Signed-off-by: Ilia Markelov <imarkelo@redhat.com>
2025-04-25 07:49:00 -04:00
ArtiomDivak 018318c844
Add copy feature for qmctl (#809)
Closes https://github.com/containers/qm/issues/803
Signed-off-by: Artiom Divak <adivak@redhat.com>
2025-04-23 19:06:11 -04:00
ArtiomDivak 735a8dc733
Add exicin for qmctl command (#816)
execin wil execute command inside a container in QM

Signed-off-by: Artiom Divak <adivak@redhat.com>
2025-04-21 15:52:06 -04:00
Douglas Landgraf a55521851e
subpackage: ros2 improvements (#814)
* subpackage ros2: add sleep infinity

Keep the container running

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

* subpackage ros2: use official fedora robotics img

quay.io/fedora-sig-robotics/ros2:jazzy-cs9

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

* subpackage: ROS2 update documentation

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

* update docs and makefile with new name

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

* Update docs/devel/experimental/SUBPACKAGES.md

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

---------

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-04-17 10:22:47 -04:00
Albert Esteve bdaec559e3
qm.container: drop sys_boot capability (#811)
A better solution would be to rely on namespaces,
but in the meantime, this helps clearing a
safety concern from assessors.

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2025-04-16 11:43:39 -04:00
Ilia Markelov 8b91f7b631
Added tty7 setup manual, fix for topics ordering (#808)
Signed-off-by: Ilia Markelov <imarkelo@redhat.com>
2025-04-15 10:49:27 -04:00
Ian Mullins 5095f24b49
Revise readthedocs content (#781)
- Minimize RTD content to serve as an appropriate starting point to improve structure.
- Introduce mkdocs-check.yml workflow

Signed-off-by: Ian Mullins <imullins@redhat.com>
2025-04-14 17:05:26 -04:00
Ilia Markelov 279289e581
Added documentation for input subpackage test (#801)
Signed-off-by: Ilia Markelov <imarkelo@redhat.com>
2025-04-14 09:04:11 -04:00
Ilia Markelov 974f65b506
Fix for video subsystem containerfile (#795)
Signed-off-by: Ilia Markelov <imarkelo@redhat.com>
2025-04-10 09:03:38 -04:00
Ilia Markelov 893417b4b6
Fix sub-package Video manual according to containerfile fix (#796)
Signed-off-by: Ilia Markelov <imarkelo@redhat.com>
2025-04-10 08:55:11 -04:00
Ian Mullins a30be64c2c
Fix setup script for older installations of Fedora (#798)
--use-host-config is only applicable to dnf5

Signed-off-by: Ian Mullins <imullins@redhat.com>
2025-04-10 08:47:33 -04:00
Yariv Rachmani 7ca5b38338
Merge pull request #785 from containers/qmtool
qmctl - QM control tool
2025-04-09 05:34:50 +03:00
Douglas Schilling Landgraf 5c1e4202d5 update description in README
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-04-08 14:45:56 -04:00
Douglas Schilling Landgraf 13c8a2c88d README: fix markdown warnings
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-04-08 12:10:57 -04:00
Douglas Schilling Landgraf 8ee206668c qmctl - QM control tool
Initial commit

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-04-08 12:10:28 -04:00
Sandro Bonazzola d96a3f587c
Removing myself from `CODEOWNERS` (#793)
I'm not really owning any code in this repository.

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2025-04-08 09:52:05 -04:00
Yariv Rachmani 69ac992063
Merge pull request #790 from containers/winmanager
subpackages: adjust path and remove qm_rootfs
2025-04-07 21:17:43 +03:00
Douglas Landgraf 80f8746fa7
add systemct daemon-reload in to the docs (#791)
podman restart qm was not enough to bring sound
container up.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-04-07 09:55:45 -04:00
Douglas Landgraf f50555cfd7
subpackages: remove dup entry in windowmanager (#792)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-04-07 09:53:31 -04:00
Yariv Rachmani a6e289ffe0
Merge pull request #789 from containers/ros2
subpackage: fix path for ros2
2025-04-07 14:45:52 +03:00
Douglas Schilling Landgraf 122677c853 subpackages: adjust path and remove qm_rootfs
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-04-06 16:25:00 -04:00
Douglas Schilling Landgraf 738632738f subpackage: fix path for ros2
- Remove old reference for qm_rootfs
- adjust ros2 for subpackage

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-04-06 16:08:58 -04:00
Yariv Rachmani d02de8f746
Merge pull request #787 from ArtiomDivak/issue-771-2
Added AddDevice=/dev/snd
2025-04-06 17:36:49 +03:00
Artiom Divak 49637001c6 Added AddDevice=/dev/snd
This MR is a corection for https://github.com/containers/qm/pull/783

related
closes https://github.com/containers/qm/issues/771
Signed-off-by: Artiom Divak <adivak@redhat.com>
2025-04-06 15:27:35 +03:00
Yariv Rachmani 1fa5ddfb83
Merge pull request #786 from containers/subvideo
subpackage: adjust spec for subpackage video
2025-04-06 09:25:12 +03:00
Douglas Schilling Landgraf eb9016d8b0 subpackage: adjust spec for subpackage video
- adjust spec for subpackage video
- add AddDevice=-/dev/video into the container file

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-04-05 16:41:36 -04:00
ArtiomDivak 1280331fbc
Container systemd-audio is not running in QM (#783)
This MR will fix the problem of systemd-audio container not runnig after
qm is up

Closes https://github.com/containers/qm/issues/771
Signed-off-by: Artiom Divak <adivak@redhat.com>
2025-04-03 09:39:02 -04:00
Yariv Rachmani 56f0b0f968
Merge pull request #764 from ArtiomDivak/document-cinf-change
Document change config in qm
2025-04-02 23:48:26 +03:00
Yariv Rachmani e8eb967ccc
Merge pull request #762 from containers/prepare_refactor
Refactoring prepare.sh
2025-04-02 23:47:51 +03:00
Pavol Brilla c91df0bc1e Suggestions added
Signed-off-by: Pavol Brilla <pbrilla@redhat.com>
2025-04-02 16:58:04 +02:00
Pavol Brilla 81d79a4ec7 Fixing last failing test (agent-flood)
agent-flood to use proper image in quadlet
returning -e to shebang of disk test
modules test added debug info message

Signed-off-by: Pavol Brilla <pbrilla@redhat.com>
2025-04-02 12:45:25 +02:00
Pavol Brilla c5da37a8c5
Merge branch 'main' into prepare_refactor 2025-04-02 10:47:46 +02:00
Artiom Divak 9db5cde521 Document change config in qm
Dodument change configuration in QM with drop-in

Signed-off-by: Artiom Divak <adivak@redhat.com>
2025-04-02 10:07:25 +03:00
Yariv Rachmani 3a95050279
Merge pull request #740 from pengshanyu/improve-disk
improve the name of var partition
2025-04-01 22:08:58 +03:00
Pavol Brilla f6cb3efadc Refactoring prepare.sh
- prepare_images:
  - removing all temporary registry location and all related items
- run_container_in_qm:
  - change calling of run_ctr_in_qm
  - if image of tools-ffi:latest is downloaded it will run directly
- clean-up:
  - as we are not doing 'podman commit' image is kept clean
  - removing image clean-up, it should speed up overall times of tests
  - clean-up is in trap (cleaning after test not before test)

Signed-off-by: Pavol Brilla <pbrilla@redhat.com>
2025-04-01 16:11:27 +02:00
pengshanyu 8f990c7f24 remove L75-79
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2025-04-01 21:54:36 +08:00
pengshanyu 5ba1055155
Merge branch 'containers:main' into improve-disk 2025-04-01 21:47:52 +08:00
Yariv Rachmani 5301363274
Adding fix for create kvm script (#779)
* Adding fix for create kvm script

Fix readme
Fix kvm container in quay
Fix kvm spec file

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

* Rebase with latest docs changes

I assume that docs/docs/index.md is not relevant

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

---------

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-04-01 08:53:02 -04:00
nsednev b7d0eda13d
Added network README.md for network options using quadlets. (#776)
Signed-off-by: nsednev <nsednev@redhat.com>
2025-04-01 08:49:51 -04:00
Yariv Rachmani 27cfd18e54
Merge pull request #777 from iamianmullins/cpu_management
docs/devel: cpu management
2025-03-31 19:55:50 +03:00
Ian Mullins e7b369c43c docs/devel: cpu management
Signed-off-by: Ian Mullins <imullins@redhat.com>
2025-03-31 11:19:38 +01:00
Douglas Landgraf 949029be51
subpackages - move it to devel/docs (#778)
* docs: remove subpackages from main README

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

* docs/devel: mention about experimantal subpackages

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

* Update docs/devel/experimental/SUBPACKAGES.md

Co-authored-by: sourcery-ai[bot] <58596630+sourcery-ai[bot]@users.noreply.github.com>
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

---------

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
Co-authored-by: sourcery-ai[bot] <58596630+sourcery-ai[bot]@users.noreply.github.com>
2025-03-28 11:28:19 -04:00
Ian Mullins e6c664db85
devel/README.md: Fix building CentOS and QM Manually documentation (#773)
Minor changes to setup and build command. The command provided currently fails.

Signed-off-by: Ian Mullins <imullins@redhat.com>
2025-03-26 13:33:39 -04:00
Lokesh Mandvekar 10585de109
CODEOWNERS: remove lsm5 (#775)
I am not actively involved in the project.

Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2025-03-25 16:15:22 +05:30
Douglas Landgraf d2c835982b
docs/devel: Show how to create tag/release (#772)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-03-20 11:43:00 -04:00
Douglas Landgraf 6f3bf2add4
README.md: add restorecon command for subpkgs (#768)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-03-19 12:56:32 -04:00
Douglas Landgraf a0ddb2dd81
README.md: update docs regarding subpackages (#767)
* README.md: update docs regarding subpackages

Remove old steps.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

* README.md: fix markdown for command

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

---------

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-03-19 11:47:08 -04:00
Yariv Rachmani 8ec51ba47e
Merge pull request #754 from engelmi/improve-qm-and-bluechi-test
Use bluechi-is-online to determine if nodes are connected or not
2025-03-19 12:58:23 +02:00
Michael Engel 9d814fc6e7
Added journalctl to agent in QM
Signed-off-by: Michael Engel <mengel@redhat.com>
2025-03-19 09:00:55 +01:00
Michael Engel eb7b9229ea
Add wait time to BlueChi check
Signed-off-by: Michael Engel <mengel@redhat.com>
2025-03-19 09:00:55 +01:00
Michael Engel 20542d7279
Removed redundant bluechi-controller e2e test
Signed-off-by: Michael Engel <mengel@redhat.com>
2025-03-19 09:00:55 +01:00
Michael Engel 9b2f82970e
Use bluechi-is-online to determine if nodes are connected or not
Signed-off-by: Michael Engel <mengel@redhat.com>
2025-03-19 09:00:55 +01:00
Douglas Landgraf 74a169bc9c
bump version for release (#760)
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2025-03-18 16:34:31 -04:00
Ian Mullins f2f13569c0
Initial setup of readthedocs documentation (#757)
Using the existing README file as a placeholder

Signed-off-by: Ian Mullins <imullins@redhat.com>
2025-03-18 11:42:24 -04:00
Yariv Rachmani 7a423be4d4
Added yaml prefix subpackages build (#746)
* Removing img_temp subpackage

Obsolted by #727

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

* Added yaml prefix

It seems that github actions for subpackage build is not working
Apdating require qm version more loose

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

* Update docs/devel/README.md

Nothing to add

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
Co-authored-by: sourcery-ai[bot] <58596630+sourcery-ai[bot]@users.noreply.github.com>

---------

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
Co-authored-by: sourcery-ai[bot] <58596630+sourcery-ai[bot]@users.noreply.github.com>
2025-03-18 11:11:27 -04:00
Yariv Rachmani 22e22781e4
Merge pull request #751 from containers/cpuweight-idle
Change CPUWeight default to "idle"
2025-03-17 19:22:06 +02:00
Alexander Larsson 3a27c8b4ed Change CPUWeight default to "idle"
This default means that the QM partition only gets CPU if nothing is
wants to run on the rest of the system. Essentially it gets SCHED_IDLE
behaviour.

Signed-off-by: Alexander Larsson <alexl@redhat.com>
2025-03-17 15:39:20 +01:00
Daniel J Walsh 157a7843f0
Merge pull request #750 from nsednev/nsednev-sound
Update NETWORK.md missing documentation.
2025-03-17 09:23:51 -04:00
Daniel J Walsh 2229e960c4
Merge pull request #749 from telemaco/ffi-vfs-safety-fixes
Improve safety in qm virtual filesystems
2025-03-17 09:22:30 -04:00
nsednev b581ff71cc Update NETWORK.md missing documentation.
Signed-off-by: nsednev <nsednev@redhat.com>
2025-03-17 14:53:17 +02:00
Roberto Majadas cb6bb2cdf3 Improve safety in qm virtual filesystems
- Removed `Unmask=ALL` from the qm.container file to enhance safety for
qm virtual filesystems.
- Set `netns="host"` as the default configuration in the
`containers.conf`.

A bit background on this. To guarantee FFI we can't have all the
sensitive pseudo-filesystems like /proc/sys and /sys fully available
inside QM. However, unfortunately currently this is needed for podman to
set up the network bridge when doing --network=private. It fails setting
some network sysctl options. For now we hack-fix this by making
non-private network default, because FFI is more important than podman
features.

However, we think long term this is fixable by granting setting some
sysctls by default in the qm container and possibly granting specific
access to safe sysctls. we did some initial work on this and got part of
the way there, but we don't have a full solution yet.

Signed-off-by: Roberto Majadas <rmajadas@redhat.com>
2025-03-17 11:14:52 +01:00
Yariv Rachmani 11aef5ccaa
Merge pull request #748 from containers/qm-cpuweight
Fix suport for CPUWeight

Remove QM.slice, run the qm service under -.slice, 
to verify QM service weights cgroups calculated based to the whole root cgroups
2025-03-17 11:26:38 +02:00
Alexander Larsson 558cc12c15 Remove references to QM.slice from docs/demos
Signed-off-by: Alexander Larsson <alexl@redhat.com>
2025-03-17 10:00:18 +01:00
Alexander Larsson 7be55d6ffa Fix suport for CPUWeight
In the current setup, qm.service is part of the QM.slice. This means
that the CPUWeight of qm.service is only applied against the other
groups of QM.slice, i.e. none. This means CPUWeight does nothing.

Here change the parent of qm.service to be -.service (the root
cgroup), which means that the weight of it will be compared to the
other toplevel slices, which normally is user.slice and system.slice.

So, with the current default CPUWeight in qm.container of 50, and the
default weight of 100, this means that qm.service now will get half
the cpu of the processes in system.slice, which is the intent.

I tried this by running "openssl speed --seconds 99999" both inside qm
and outside it one a one-cpu VM, and before both processes always got
50% cpu, but now they are split up according to CPUWeight in the
qm.container.

Signed-off-by: Alexander Larsson <alexl@redhat.com>
2025-03-14 17:47:12 +01:00
pengshanyu 6558b5b63a improve the name of var partition
Signed-off-by: pengshanyu <yupengshan@hotmail.com>

improve oom.conf;improve variable names

improve PodmanArgs
2025-03-06 14:11:15 +08:00
Yariv Rachmani 59bc58b38e
Merge pull request #745 from Yarboa/packit_release
Updating release build for c10s
2025-03-06 00:12:05 +02:00
Yariv Rachmani 21c9895b25 Updating release build for c10s
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-03-05 22:55:17 +02:00
Douglas Landgraf d4a5732ebd
bump to v0.7.3 (#744)w
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2025-03-05 15:32:07 -05:00
Yariv Rachmani c74db387c2
Merge pull request #743 from containers/fix-network-subnet
containers.conf: Set a different default ip subnet for qm containers
2025-03-05 21:13:53 +02:00
Alexander Larsson 38374ff2c7 containers.conf: Set a different default ip subnet for qm containers
Otherwise both host and qm containers have the same range and things get
confused.

Signed-off-by: Alexander Larsson <alexl@redhat.com>
2025-03-05 16:52:23 +01:00
Yariv Rachmani 6e15f6cba5
Merge pull request #742 from containers/fix-qm-selinux-mmap-dev-zero
Selinux: Allow qm_t to mmap qm_file_t char devices
2025-03-04 12:26:57 +02:00
Alexander Larsson 05cfa40e7e Selinux: Allow qm_t to mmap qm_file_t char devices
This allows qm apps to mmap /dev/zero which is a common operation, and
should be safe.

Fixes: https://github.com/containers/qm/issues/741
Signed-off-by: Alexander Larsson <alexl@redhat.com>
2025-03-04 09:12:17 +01:00
Douglas Landgraf c95f521942
update VERSION to 0.7.2 (#738)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-02-28 16:27:52 -05:00
Douglas Landgraf 950f07d91b
spec: in case host don't have ip_tables proceed (#737)
Resolves: https://github.com/containers/qm/issues/736

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-02-28 14:53:19 -05:00
Yariv Rachmani a09ba109d9
Fix merge errors (#735)
resolve #677

There is misssing target for epel-10
There is missing dependency bluechi-selinux exist in epel and not c10s

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-02-27 16:23:20 -05:00
Douglas Landgraf 2e485b84f7
bump version to 0.7.1 (#733)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-02-27 09:50:10 -05:00
Alexander Larsson b7264e4c15
qm.spec: Fix packaing for other selinux policies (#731)
The current package hardcodes that post-install it will install the
module to the "targeted" policy (but the macro only does this is it is
also the active policy). This means if the active policy is something
else, such as "automotive", then the qm module is not installed at
all, and qm doesn't work.

We fix this by always installing the module to the active selinux policy.
This is how e.g. container-selinux does it.

In addition we remove the hard post-require on selinux-policy-target
and replace it with selinux-policy-any, which all selinux policy
packages provide. We also add a recommendataion of
selinux-policy-targeted, so most people get it. This is also what
container-selinux does.

Signed-off-by: Alexander Larsson <alexl@redhat.com>
2025-02-27 09:13:44 -05:00
Douglas Landgraf eda62c8931
release version 0.7.0 (#729)
Resolves: https://github.com/containers/qm/issues/728

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-02-26 17:16:00 -05:00
Douglas Landgraf caa22ea148
qm.container: add tmpfs additional flags (#727)
Resolves: https://github.com/containers/qm/issues/723

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-02-26 11:36:42 -05:00
nsednev 6666250f0f
Adding a link to NETWORK.md from the main README.md (#726)
Signed-off-by: nsednev <nsednev@redhat.com>
2025-02-18 08:53:00 -05:00
Yariv Rachmani 1729549b42
Updating submodule packages to drop-ins quadlet files (#700)
* Updating submodule packages to drop-ins quadlet files

resolves #674
During latest changes all subpackages use drop-in qudlet files
Under QM etc/containers/systemd/qm.container.d/ dir
Qm nested container quadlets moved to subsystems/ dir
Update to quadlet files

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

* Fix subpackages make file

It seems that subpackaged rpm was not set correctly
Make subpackages creation could be done with the following command
make TARGETS=kvm subpackages

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

* make TARGETS=windowmanager subpackages

make TARGETS=windowmanager subpackages
Adding missing qm qualets

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

* make TARGETS=sound subpackages

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

* make TARGETS=video subpackages

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

* Adding more targets

make TARGETS=dvb subpackages
make TARGETS=img_tmpdir subpackages
make TARGETS=input subpackages
make TARGETS=radio subpackages
make TARGETS=tesxt2speech subpackages
make TARGETS=tty7 subpackages
make TARGETS=ttyUSB0 subpackages

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

* Add target ros2

make TARGETS=ros2 subpackages
Adding github workflow for subpackages
renaming rpm/ros2/rolling/ros2_rolling.spec ->
rpm/ros2/ros2_rolling.spec

Adding fixes based on tests added

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>

---------

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-02-15 10:15:50 -05:00
nsednev a7966f2fa1
Added NETWORK.md explaining network=host and network=private functionality with default settings of private because of security enforcements. (#713)
Signed-off-by: nsednev <nsednev@redhat.com>
2025-02-10 09:45:48 -05:00
Yariv Rachmani 16a3ca7cbd
Merge pull request #710 from pengshanyu/add-comment-for-service
add comments to qm.container service
2025-02-06 12:29:52 +02:00
Yariv Rachmani e67a9090e0
Merge pull request #716 from Yarboa/public-tf-compose
Adding packit kvm-test temporary-fix
2025-02-06 12:28:44 +02:00
Yariv Rachmani 071586d647 Adding packit kvm-test temporary-fix
Due to this
https://github.com/containers/qm/pull/710/checks?check_run_id=36772216370
Chenged packit kvm test frpm fedora-latest -> fedora-41

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-02-06 11:34:37 +02:00
pengshanyu 1c53e0f14c add comment to service
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2025-02-05 10:57:35 +08:00
Douglas Schilling Landgraf 9950dd1af0 fix bandit check
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-01-30 11:03:32 -05:00
Douglas Schilling Landgraf 27d33364ce README: add a note about how to enable realtime
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-01-30 11:03:32 -05:00
Douglas Schilling Landgraf 236ad09377 rename /usr/share/qm/seccomp.json
To be explicit the current seccomp.json
DO NOT support realtime (rt) sched we will
add it into the name of the file.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-01-30 08:53:56 -05:00
Yariv Rachmani 5d71cc01ed
Merge pull request #678 from ilimarx/qm_container_doc
Adding comments for container options in qm.container
2025-01-29 18:47:40 +02:00
Ilia Markelov 837517ce1e Add comments to container options
Signed-off-by: Ilia Markelov <imarkelo@redhat.com>
2025-01-28 15:02:03 +01:00
Yariv Rachmani 6b63a11d7c
Merge pull request #708 from engelmi/add-epel10-bluechi-copr
Added epel10 additional repos to copr build
2025-01-21 08:54:07 +02:00
Douglas Schilling Landgraf 009b5a4f66 Makefile: make rpm should only generate qm
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-01-20 20:14:18 -05:00
Michael Engel acda4fabd3
Added epel10 additional repos to copr build
Relates to: https://github.com/containers/qm/issues/677

Added bluechi copr repo as additional repo to epel10 copr build job target

Signed-off-by: Michael Engel <mengel@redhat.com>
2025-01-20 14:42:01 +01:00
Mark Kemel 0ccc4695be Add jq package installation to a-i-b test
auto-image-builder.sh now uses jq. Adding jq to the prepare step for
automotive-image-builder test plan

Signed-off-by: Mark Kemel <mkemel@redhat.com>
2025-01-20 07:06:49 -05:00
Yariv Rachmani 4f3a2eb170
Merge pull request #703 from engelmi/add-bluechi-uds-to-policy
Add bluechi uds to policy
2025-01-16 21:13:38 +02:00
Yariv Rachmani 2aa35bb6fc
Merge pull request #697 from mkemel/aib-ci
Add test to run basic qm image build with a-i-b
2025-01-16 13:30:38 +02:00
Michael Engel 6459e7eca8
Extended SELinux policy to support BlueChi UDS
Fixes: https://github.com/containers/qm/issues/677

Recently, BlueChi enhanced the support for Unix Domain Sockets,
including the respective SELinux policy (see In eclipse-bluechi/bluechi#1015).
On a setup QM + BlueChi it makes sense to mount the UDS of BlueChi into QM
and have the bluechi-agent inside connect to it. This, however, is currently
rejected due to missing SELinux policy rules. Let's add this rule.

Signed-off-by: Michael Engel <mengel@redhat.com>
2025-01-16 10:31:46 +01:00
Michael Engel 73b5a9062d
Removed bluechi-agent dependency in QM
Signed-off-by: Michael Engel <mengel@redhat.com>
2025-01-16 10:31:46 +01:00
Mark Kemel dc8e8b8e4c Add test to run basic qm image build with a-i-b
Introducing a new sanity test, that builds a basic qm image with
automotive-image-builder.

Signed-off-by: Mark Kemel <mkemel@redhat.com>
2025-01-16 09:11:55 +02:00
Yariv Rachmani ff43278404 ros2 split makefile
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-01-14 09:10:09 -05:00
Yariv Rachmani 6bab941c56 make split
- dvb
- radio
- tty7
- input
- ttyUSB0
- text2speech
- img_tempdir

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-01-14 09:10:09 -05:00
Yariv Rachmani ab4567c918 video make split
Moving tests container, makefile to specific
subsys directory

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-01-14 09:10:09 -05:00
Yariv Rachmani 8cfb3b6549 split sound make
Moving tests container, makefile to specific
subsys directory

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-01-14 09:10:09 -05:00
Yariv Rachmani d6b4c7acee Split windowmanager makefile
renamed qm-windowmanager -> windowmanager
move windowmanager to subsystems
add windowmanager Makefile

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-01-14 09:10:09 -05:00
Super User 07132460c8 Makefile-split
split kvm makefile

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2025-01-14 09:10:09 -05:00
Yariv Rachmani 91de011371
Merge pull request #698 from gjacobRH/add_metadata
Adding test metadata for validators
2025-01-12 10:43:37 +02:00
George Jacob 488f2ea18e Added missing metadata needed for validators
Signed-off-by: George Jacob <gjacob@gjacob-thinkpadt14sgen2i.remote.csb>

Removed trailing spaces

Signed-off-by: George Jacob <gjacob@gjacob-thinkpadt14sgen2i.remote.csb>

Fixed spacing and spelling issues

Signed-off-by: George Jacob <gjacob@gjacob-thinkpadt14sgen2i.remote.csb>
2025-01-09 10:17:19 -06:00
Douglas Schilling Landgraf dc06790fd5 text2speech: add espeak to QM
When adding base robotic to QM, it's always good to have
text2speech available for development. Specially for demos, talks.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-01-04 07:49:21 -05:00
Douglas Schilling Landgraf 5935d88e9d release 0.6.9
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-01-04 07:02:55 -05:00
Douglas Schilling Landgraf 863ca5d523 set rpm version to 0 for autorpm work
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-01-04 07:02:55 -05:00
Douglas Schilling Landgraf a19d593165 setup: Avoid SecurityLabelNested for CentOS <=9
During tests show it's incompatible.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-01-04 06:21:55 -05:00
Douglas Schilling Landgraf 0ef4f3d37e fix requirement of modprobe ip_tablesfix requ
- netavark requires ip_tables, otherwise podman complains
- removed in %post isostres command (not required at all)

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-01-04 06:21:55 -05:00
Douglas Schilling Landgraf 3eba152036 subpackage dvb
dvb is a subpackage for digital TV. Allow developers to
emmulate digital tv inside QM.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-01-01 17:03:34 -05:00
Douglas Schilling Landgraf c3e3a47b1a introduction subpackage radio
It's possible to simulate via opensource cars with
webcams, radios devices and even digital tvs, here
another extension to QM.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2025-01-01 10:05:23 -05:00
Douglas Schilling Landgraf ef5463d68b README: update readme with new subpackage split schema
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-31 11:31:02 -05:00
Douglas Schilling Landgraf d17888b7e8 rpm spec split: split windowmanager
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-31 09:49:48 -05:00
Douglas Schilling Landgraf 97d3ad1f8a split spec file, move img_tempdir to it's own spec
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-31 06:43:48 -05:00
Douglas Schilling Landgraf 4359aec149 split rpm spec for ttyUSB0
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-31 06:05:44 -05:00
Douglas Schilling Landgraf 4e3252d319 split packaging: input now has it's own spec
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-31 05:31:29 -05:00
Douglas Schilling Landgraf 8f4d5cabb3 spec: remove old tty7 spec thing
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-31 04:49:19 -05:00
Douglas Schilling Landgraf 6b6db9ddde tools and rpm chmod +x
tools that we execute should be chmod +x

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-31 04:49:19 -05:00
Douglas Schilling Landgraf 07824ae976 gitignore: add *.tar.gz
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-31 04:49:19 -05:00
Douglas Schilling Landgraf 8fdc8c3d4a spec: split tty7 into single spec
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-31 04:49:19 -05:00
Douglas Schilling Landgraf 78cea34772 split subpackage video into single spec
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-31 03:06:37 -05:00
Douglas Schilling Landgraf ab493daf2e subpackage sound split in it's own spec
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-30 20:43:40 -05:00
Douglas Schilling Landgraf 0b38e6e3bb split subpackage ros2 rolling
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-30 20:09:41 -05:00
Douglas Schilling Landgraf 93e3f51fa5 subpackage: split qm kvm into sep package
As requested split the kvm subpackage in a specific package.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-12-30 18:49:31 -05:00
Yariv Rachmani cac73007b2 Adding build script for kvm
To reduce size and time od contianer quay.io/qm-images/kvm
Build, qcow2 images is manipulated on host

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-12-11 22:22:10 -05:00
Douglas Schilling Landgraf 3ae7b49c64 [WIP]: use quay.io qm - kvm
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-12-11 22:22:10 -05:00
Yariv Rachmani 14829855f3
Merge pull request #673 from pengshanyu/improve-disk
check /var partition before run /tests/ffi/disk
2024-12-05 16:59:47 +02:00
Yariv Rachmani 4a9bec30b4
Merge pull request #672 from containers/specrmcreationdirs
spec: remove the dirs creations
2024-12-05 16:43:03 +02:00
Douglas Schilling Landgraf 4551d9b33d qm.spec: use mkdir -p in the buildroot
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-04 18:35:31 -05:00
Douglas Schilling Landgraf 637417ef65 github actions: remove drop-in target build
It's based in the currect spec, later we re-add in the new schema.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-04 18:25:11 -05:00
Douglas Schilling Landgraf 3b907fc1ed spec: remove the dirs creations
It should go directly in the subpackages which requires it.
On top of that it BROKE autosd installer with mkdir -EEXIST.

/usr/lib/qm/rootfs/etc
/usr/lib/qm/rootfs/etc/containers
/usr/lib/qm/rootfs/etc/containers/system

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-12-04 18:16:43 -05:00
pengshanyu d5c11a7793 check /var partition before run it
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-12-04 17:01:31 +08:00
Yariv Rachmani 7ae21417a3
Merge pull request #670 from Yarboa/kvm-test
Add fedora fix
2024-12-03 11:35:22 +02:00
Yariv Rachmani 9e0550ebb2 Add fedora fix
Fedora tests run only on kvm-tier-0
This commit resolves #666, till full support in podman
c9s, added fix in set-ffi-env-e2e
Fix setup script, unmount qm nounts before dnf remove qm

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-12-03 11:10:19 +02:00
Yariv Rachmani 7d48592ee5 Adding KVM tier-0 rpm subpackage testing
KVM tier-0 tests dedicated for kvm tests.
It checks /dev/kvm. nested virtualization exist.
In case not, it removes qm_mount_bind_kvm rpm, in case installed by packit.

Test check_qm_setup_succeeds is the irst test to run,
The test check repo setup script is working properly

Packit support for nested kvm support added currently for fedora/c9s
Kvm tests should be introduced later.
Introducing QM quadlets drop-ins for extending qm.container base quadlet.
Using as single point of configuration.
Replacing the usage of containers.conf

Fedora is failing due to #666

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-11-28 10:19:39 -05:00
Yariv Rachmani da70aa5980 Adding supported quadlet vars mappings
Remove PodmanArgs, since the following mappings supported:
rpm -q podman
podman-5.2.3-6.el9.x86_64

Unmask=ALL
SecurityLabelNested=true
SeccompProfile=/usr/share/qm/seccomp.json
PidsLimit=-1

Adding Readme related to updating qm quadlet file
It seems that currently there is usage in
/etc/qm/containers/containers.conf
Instead of extension of existing quadlet

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-11-27 01:56:47 -05:00
Albert Esteve 1b6a02a7de tests/ffi/sys_read_only: add polarion id
Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-11-27 00:06:03 -05:00
Albert Esteve e573bccee0 tests/ffi: add test checking /sys is read-only
Test to ensure that /sys is read-only inside the
QM container.

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-11-27 00:06:03 -05:00
Yariv Rachmani e5bc702528 Adding extra packages to fix-spec-file
+ Rebase latest changes
+ Adding howto create PR subpackages

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-11-18 03:18:28 -05:00
Douglas Schilling Landgraf e2ad952464 ros2: update containterfile to use fedora:latest
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-11-13 16:17:10 -05:00
Douglas Schilling Landgraf 9f4d78bc0e release: v0.6.8
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-11-13 00:13:16 -05:00
Douglas Landgraf cc031d0454 Update tests/e2e/README.md
Co-authored-by: Nikola Forró <nforro@redhat.com>
2024-11-12 14:49:48 -05:00
Yariv Rachmani d483f5e4b5 Fedora-support
Prepare Fedora image for testing
Changing the copr repositories to more genereric way
README explains how to tests copr PR rpm on local vm
For cases without /etc/os-release added distro context
to env-variable

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-11-12 14:49:48 -05:00
Douglas Schilling Landgraf b4635b1901 subsystem: add audio dir
Add audio dir with ContaineFile with all packages required for
quadlets when the subject is add initial audio support.

Signed-off-by: Douglas Schilling Landgraf <dlandgra@redhat.com>
2024-11-11 05:26:06 -05:00
Douglas Schilling Landgraf 5826e1c758 packit: add fedora
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-11-10 06:46:14 -05:00
Douglas Schilling Landgraf c409c8bde5 setup: for fedora use --use-host-config for dnf repos
It will solve the recent CI/CD setup install complain
about not able to find packages.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-11-09 21:28:40 -05:00
pengshanyu 848b5f4a9a add NoRenesas tag
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-11-08 09:50:09 -05:00
Douglas Schilling Landgraf 1601fce179 drop-in-target-build-only: use f40
rawhide is often broken better use latest stable.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-11-03 08:33:27 -05:00
Douglas Schilling Landgraf 2f8ed3a870 docs: debugging quadlets
Just useful information for devs how to debug quadlets.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-11-03 08:33:27 -05:00
Douglas Schilling Landgraf d147a9c47a ros2-rolling: remove the restart action
Not supported avoiding the image download.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-11-03 08:33:27 -05:00
Douglas Landgraf 561050f0bd WIP: Add ROS2 subpackage into QM
Just initial work to support ROS2 - "The Robot Operational System" (The middleware for robots) out of box into QM.

ContainerFile by Leonardo Rossetti <lrossett@redhat.com> with few mods by me.

See-Also: https://ros.org/

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-10-30 20:37:20 -04:00
Douglas Schilling Landgraf 22c2c00872 spec: remove ghost entry for qm.container
During service start in Fedora it try to read
qm.container from /etc/containers/systemd/qm.container
instead of /usr/share/qm/qm.container and fails
as it's a ghost (empty) file.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-10-30 20:09:23 -04:00
Douglas Schilling Landgraf 6f4636ce15 test: add check_qm_setup_succeeds
check if setup script works

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-10-30 07:15:08 -04:00
Yariv Rachmani aa32b1d9a4 Add packit pre-commit
Fix #634

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-10-28 13:19:04 -04:00
Douglas Schilling Landgraf 5b6b21df2a README: adding few words into the video part
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-10-25 13:30:33 -04:00
Douglas Landgraf ce35fd9fed README: add session about VIDEOS related to QM
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-10-25 13:03:31 -04:00
Douglas Landgraf a194cd2160 github-actions: add test to build dropin targets
Just test if make dropin targets works

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-10-24 15:30:58 -04:00
Douglas Landgraf 2cb6d3e9bd README: fix TOC in main README
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-10-24 13:40:19 -04:00
Douglas Landgraf a1c7f8d5c6 qm-windowmanager: update content
- update dirs and files

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-10-17 08:31:35 -04:00
Nikola Forró e382fa9fe4 Simplify references to BlueChi Copr repo in Packit config
Signed-off-by: Nikola Forró <nforro@redhat.com>
2024-10-16 11:37:05 -04:00
Nikola Forró d8b47a3a27 Use EPEL targets to simplify Packit configuration
`epel-9` chroot in Copr is RHEL 9 with EPEL repo enabled.
As for Testing Farm, both `centos-stream-9-x86_64` and `epel-9-x86_64`
targets map to the same CentOS Stream 9 compose. EPEL repo is always
enabled there.

Signed-off-by: Nikola Forró <nforro@redhat.com>
2024-10-16 11:37:05 -04:00
Nikola Forró 43e0c7f245 Fix Packit configuration
Signed-off-by: Nikola Forró <nforro@redhat.com>
2024-10-16 06:08:33 -04:00
Douglas Landgraf cbe21d6fb5 Makefile: reduce payload in dist target
reduce payload in the dist target

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-10-14 21:23:45 -04:00
Douglas Landgraf 4feb349982 Makefile: fix missing \
Recently we changed the way to do builds, adding the missing \

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-10-14 17:04:33 -04:00
Rakesh Musalay 1cd84ffe8e typo mistake change to qm-os-tree
Signed-off-by: Rakesh Musalay <rmusalay@redhat.com>
2024-10-14 07:39:46 -04:00
Rakesh Musalay 8011840cc2 Add qm-is-ostree script installation and RPM packaging
- Updated Makefile to install the qm-is-ostree script to ${DATADIR}/qm/
- Modified qm.spec to include qm-is-ostree in the install and package files
- Added the qm-is-ostree script to the RPM preuninstall stepsw
Signed-off-by: Rakesh Musalay <rmusalay@redhat.com>
2024-10-14 07:39:46 -04:00
Yariv Rachmani ba373d0068 Adding VARIABLES for subpackages
Adding u_variable to be set with default envvars in Makefile
Rebase with main branch
Adding default variables in case not defined

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-10-14 07:39:31 -04:00
pengshanyu 206e99d4a6 fix prune
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-10-13 23:57:23 -04:00
Douglas Schilling Landgraf 76cf0c7f21 qm subpackage: simulate car cameras using OSS
In a typical vehicle system, cameras are connected to the car's onboard
computer via a CAN bus (Controller Area Network), which transmits signals
from the cameras to the car’s system for real-time processing.
This is commonly used for functions like parking assistance, lane-keeping,
or 360-degree surround-view systems.

However, it's possible to create a simulation environment using traditional
hardware and open-source software, eliminating the need for actual car cameras
or CAN bus integration. By using open-source tools like Podman containers and
video processing libraries (such as GStreamer or FFmpeg), virtual cameras can
be simulated. These tools allow developers to simulate the video signals
typically produced by physical car cameras and routed through the CAN bus.

In this setup, virtual devices (e.g., /dev/video0, /dev/video1) are mounted
into a container and can provide simulated video streams that mimic real
camera feeds. This allows automotive software to be developed and tested in a
controlled environment, replicating the behavior of car cameras without
needing access to the physical hardware or CAN bus.

Signed-off-by: Douglas Schilling Landgraf <dlandgra@redhat.com>
2024-10-13 10:02:21 -04:00
Douglas Schilling Landgraf 10578f6641 QM subpackage: Wayland
Developed by Albert and Roberto, integrating to QM upstream as sub-package.
This is an initial patch, I am sure we will need more work but let's
make it happen!

Use: make qm_dropin_window_manager

Ref:
https://aesteve-rh.github.io/alesgar-digital-cockpit/posts/wayland-in-qm/

Signed-off-by: Douglas Schilling Landgraf <dlandgra@redhat.com>
2024-10-09 07:45:56 -04:00
Yariv Rachmani 068c26df3c
Merge pull request #608 from containers/kvm
qm sub-package Kernel-based Virtual Machine (KVM)
2024-10-08 16:38:26 +03:00
Douglas Schilling Landgraf 077c2bb28d qm sub-package Kernel-based Virtual Machine (KVM)
The QM sub-package KVM includes drop-in configuration that enables the
integration of Kernel-based Virtual Machine (KVM) management into the
QM (Quality Management) container environment. This configuration allows
users to easily configure and manage KVM virtual machines within the QM
system, streamlining virtualization tasks in containerized setups.

Use: make qm_dropin_mount_bind_kvm

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-10-08 03:07:00 -04:00
Albert Esteve d97d144471 makefile: update version in rpm target
Call the update-version script from the
rpm target in the makefile and remove it
from all the subpackage targets, so that
we have a single point of failure and
avoid code repetition.

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-10-07 12:54:18 -04:00
Douglas Schilling Landgraf f58c315bef qm sound sub-package: enable audio
Enable audio in QM container and nested containers

Signed-off-by: Douglas Schilling Landgraf <dlandgra@redhat.com>
2024-10-07 10:05:59 -04:00
Yariv Rachmani c49711eefd Remove -e from set-ffi-env-e2e
It fails script on non c9s distros

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-10-06 22:47:34 -04:00
Douglas Schilling Landgraf 26cbbb5cb4 qm sub-package qm_dropin_mount_bind_ttyUSB0
Another ready to use example in-tree to users.
Execute: make qm_dropin_mount_bind_ttyUSB0 and voi-la.

Signed-off-by: Douglas Schilling Landgraf <dlandgra@redhat.com>
2024-10-06 08:28:06 -04:00
Yariv Rachmani 93e540ea92 Added fix to c9s
Under CI special case exist.
rpm qm is installed in c9s machine, but setup
script that emulate the QM environment is not set

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-10-06 07:59:51 -04:00
Douglas Schilling Landgraf 84e090c10d README: fix pre-commit warnings
Signed-off-by: Douglas Schilling Landgraf <dlandgra@redhat.com>
2024-10-05 08:49:57 -04:00
Rakesh Musalay 645c4d7ee8 Update Fedora and EPEL branch targets to architecture-specific branches in .packit.yaml
Signed-off-by: Rakesh Musalay <rmusalay@redhat.com>
2024-10-04 19:23:06 -04:00
Douglas Schilling Landgraf 049d022ff1 README: add restart note about QM after subpkg
Signed-off-by: Douglas Schilling Landgraf <dlandgra@redhat.com>
2024-10-04 08:49:48 -04:00
Douglas Schilling Landgraf 3c2b51498f README: add TOC and QM subpackages info
Signed-off-by: Douglas Schilling Landgraf <dlandgra@redhat.com>
2024-10-04 08:32:45 -04:00
Douglas Schilling Landgraf cd2365f73e makefile: use update-version tool
Signed-off-by: Douglas Schilling Landgraf <dlandgra@redhat.com>
2024-10-04 00:05:57 -04:00
Douglas Schilling Landgraf dbc8d50b1b qm sub-package qm_dropin_mount_bind_input
QM sub-package qm_dropin_mount_bind_input will configure via
drop-in /dev/input to allow nested containers to automatically
see devices like: Keyboards, Mice, Touchpads, Joysticks,
Multimedia keys and Device files like /dev/input/event0,
/dev/input/event1, etc.

Just execute: make qm_dropin_mount_bind_input

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-10-03 23:57:25 -04:00
Nikola Forró df4232c11a Add Fedora 41 and drop Fedora 38 from Packit config
Signed-off-by: Nikola Forró <nforro@redhat.com>
2024-10-03 22:18:21 -04:00
Douglas Schilling Landgraf d60ede6de7 makefile: replace make with $(MAKE)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-10-03 14:42:13 -04:00
Albert Esteve b8b3e1a0a9 tools/version-update: script to manage version
Create a script to ease version managing for
maintainers and developers. The script will handle
updating the version in all required files
consistently.

By default, if no new version is provided, the
script increases the minor version by 1.
Otherwise, a specific version can be set with:

$ tools/version-update --version 1.0

And the tools will just perform the changes in
all the relevant files.

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-10-03 09:40:10 -04:00
Douglas Schilling Landgraf 2ab9dbeee6 qm subpackage - qm_mount_bind_tty7
/dev/tty7 is typically the virtual terminal associated
with the graphical user interface (GUI) on Linux systems.
It is where the X server or the Wayland display server usually runs,
handling the graphical display, input, and windowing environment.
When you start a graphical session (such as GNOME, KDE, etc.),
it usually runs on this virtual console. This patch mount bind
/dev/tty7 to QM container and also to the nested containers.

Just run: make qm_dropin_mount_bind_tty7

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-10-03 08:39:15 -04:00
Douglas Schilling Landgraf 4d9e753105 makefile: add help - usage
help users to understand what options we have.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-10-02 09:56:26 -04:00
Douglas Schilling Landgraf 402a3701f4 qm: introduction to qm dropin sub-packages(s)
QM developers are always looking for ways to help new users and
engineers onboard more easily. With this in mind, they decided
to break complex configurations into drop-in sub-package(s) when
 possible for adjusting the Podman engine configurations specifically
within the QM environment. Why? This approach provides an easy way to
extend or override settings without modifying the core (original)
configuration files.

Signed-off-by: Douglas Schilling Landgraf <dlandgra@redhat.com>
2024-10-02 09:56:26 -04:00
nsednev 26ba84b3aa Fix: ostree images, pulling container larger than 0.9M
Signed-off-by: nsednev <nsednev@redhat.com>
2024-09-27 05:22:44 -04:00
Yariv Rachmani 67a9d9a876
Merge pull request #582 from containers/codeowners
CODEOWNERS: add kleinffm for CODEOWNERS
2024-09-23 00:05:27 +03:00
Douglas Schilling Landgraf 9b0bbf09d8 CODEOWNERS: add kleinffm for CODEOWNERS
Felicia has being working in docs in the entire automobile
project. I would like to suggest Felicia as co-maintainer of QM project
so she is able to keep her sharp eyes in the docs and in the project as
well so we follow all the docs good practices and also make sure we
include in our new patches documentation so in few year nobody get lost.

Signed-off-by: Douglas Schilling Landgraf <dlandgra@redhat.com>
2024-09-22 10:13:56 -04:00
Albert Esteve ed4d501c1f qm.if: allow kvm connectto unix_stream_socket
This rule covers the ase of a qm_container_kvm_t
container (e.g., containerized qemu) to work
with dbus display.

Also covers the usecase for vhost-user devices,
as they use unix sockets to communicate with the
VMM (that is, assuming they also use the
qm_container_kvm_t type label).

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-09-19 18:05:19 -04:00
pengshanyu c3e66f1a0d add back agent-flood
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-09-19 18:03:02 -04:00
pengshanyu e2af86948b imporve the clean step
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-09-19 04:01:15 -04:00
Douglas Landgraf a5c3abb605 qm.container: add MemoryMax and MemoryHigh
Add new settings for [Service]

See-Also: https://gitlab.com/CentOS/automotive/src/automotive-image-builder/-/merge_requests/102

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-13 08:35:22 -04:00
Douglas Landgraf 79ce2222d9 check_run_systemd_journal_socket: add fail case for socket
If host do not have the socket, let's fail right away

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-12 23:34:06 -04:00
Douglas Landgraf a0a1cacac5 version v0.6.7
let's bump version before tag

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-12 17:43:47 -04:00
Douglas Landgraf 1447246512 qm: bump version
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-12 15:44:53 -04:00
Yariv Rachmani a275ad45c2 Adding fix in qm cleanup for disk tests
During the work of post install /var/qm partition
podman rmi throws error on cleanup.
This error fails the tests

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-09-12 13:07:41 -04:00
Douglas Landgraf 1851e19668 packit: add support to EPEL10
Add support to EPEL10 releases

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-12 12:02:14 -04:00
Douglas Landgraf be96b80706 CODEOWNERS: reflect contributions
update CODEOWNERS with active contributors

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-12 12:01:36 -04:00
Douglas Landgraf f61b5c5cf1 github actions: more debug about cgroups failure
We are investigating CI/CD failure regarding cgroupsv2

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-12 12:01:22 -04:00
Douglas Landgraf 49da5e2403 diskutils: add status
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-11 12:43:29 -04:00
Douglas Landgraf eace5c70b5 diskutils: add status qm
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-11 12:43:29 -04:00
Douglas Landgraf b3d8f40f44 diskutils: only remove dirs that not mounted
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-11 12:43:29 -04:00
Yariv Rachmani d0cf966934 remove mounts on /var
on SoC stop qm mounting
check if parted is installed

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-09-11 12:43:29 -04:00
Douglas Landgraf 513167c208 improve qm-oom-score-adj logic
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-11 12:43:29 -04:00
Douglas Landgraf 2de345e6d5 tests/diskutils: use pure partprobe
No need to be specific for disk, lets to the whole thing

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-11 12:43:29 -04:00
Douglas Landgraf 74529a28dc Remove #!/bin/bash -euvx options
The shebang (#!) at the beginning of the line indicates that the script should be executed using the specified interpreter, which in this case is /bin/bash. This means that the script will be run using the Bash shell.

Signed-off-by: nsednev <nsednev@redhat.com>
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-11 12:43:29 -04:00
Douglas Landgraf 756947df06 refactory tests disks
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-11 12:43:29 -04:00
Douglas Landgraf 6b2a7e9d58 tests: add parted to rescan the disks
parted is supported in archs we are testing

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-06 18:03:22 -04:00
nsednev 515a26ee6d Rebase for VROOM-22506.
Signed-off-by: nsednev <nsednev@redhat.com>
2024-09-06 18:01:54 -04:00
Daniel J Walsh 64fc09a13b
Merge pull request #535 from rhatdan/selinux
Allow qm_t ipc_lock capabilty
2024-09-03 14:20:34 -04:00
Daniel J Walsh dbc6c64e54
Merge pull request #516 from aesteve-rh/qemu-kvm
qm.if: qemu + gtk display with wayland
2024-09-03 14:19:58 -04:00
Daniel J Walsh dbe7d25606
Allow qm_t ipc_lock capabilty
Fixes: https://issues.redhat.com/browse/RHEL-56385

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2024-09-03 11:31:07 -04:00
Douglas Landgraf 96ff300807 main.fmf: add test macro
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-03 06:23:22 -04:00
Douglas Landgraf a69551f97f skip agent-flood test it's failing
lets dig it in a different report.

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-03 06:23:22 -04:00
Douglas Landgraf 0c0e8a7460 test.sh: more improvements in bash
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-03 06:23:22 -04:00
Douglas Landgraf 9d4c953cb4 diskutils: add partprobe after changing fdisk
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-03 06:23:22 -04:00
Douglas Landgraf 46c8a966e0 add more debug lines
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-03 06:23:22 -04:00
Douglas Landgraf 6ff1538d59 oom-score: retry in case container pid not ready
test has being failing, let's retry to catch the
pid 10x before exiting.

Fixes: https://github.com/containers/qm/issues/523

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-03 06:23:22 -04:00
Albert Esteve 270e21ddf7 qm.if: qemu + gtk display with wayland
These rules are collected for an scenario
where a Qemu KVM container runs with GTK
display and Wayland compositor.

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-09-02 14:51:41 +02:00
Douglas Landgraf 3000572a0f workflow: add bandit check
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-01 16:04:25 -04:00
Yariv Rachmani 7e4d52acfc
Merge pull request #527 from containers/invoke
e2e: car-dashboard - use invoke
2024-09-01 19:38:27 +03:00
Douglas Landgraf 33b7df839f e2e: car-dashboard - use invoke
replace subprocess with invoke

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-09-01 03:17:12 -04:00
Yariv Rachmani 4fe14203dd Add support for SoC separate var partition
Updating tests/e2e/set-ffi-env-e2e to mkfs.ext4
On free sde partiton it finds
Move disk functions to lib/diskutils script
Increase timers for memory and qm-oom-score-adj

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-08-31 08:05:30 -04:00
Douglas Landgraf 326aacf4c9 demos: Add slide from DevConf.US FFI
Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-08-30 09:30:46 -04:00
pengshanyu 1c969c8c49 remove the insertion of agent.conf
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-08-29 19:48:10 -04:00
nsednev 32bb6d35a8 Refine comments in tcp_max_syn_backlog
Signed-off-by: nsednev <nsednev@redhat.com>
2024-08-28 09:20:26 -04:00
Yariv Rachmani 282f04da53 add support in QM image
In case QM already runnig as a service
tests/e2e/set-ffi-env-e2e will exit 0
in case service does not exist,
it will contine
In case of ostree image script will exit

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-08-27 13:35:48 -04:00
Douglas Landgraf 6640439547 gh actions: add cgroup checker
Display the cgroup version from the worker

Signed-off-by: Douglas Landgraf <dlandgra@redhat.com>
2024-08-23 17:12:29 -04:00
nsednev 8b7ff62ff2 Rebase for qm_nested patch
Signed-off-by: nsednev <nsednev@redhat.com>
2024-08-23 14:32:01 -04:00
nsednev ad4e074d26 Patch for common.sh
Signed-off-by: nsednev <nsednev@redhat.com>
2024-08-22 17:44:14 -04:00
pengshanyu 88883751db improve prepare_images;increase duration
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-08-22 14:29:05 -04:00
nsednev 37987e0a37 Nested QM test to new fork
Signed-off-by: nsednev <nsednev@redhat.com>
2024-08-22 14:26:10 -04:00
pengshanyu 615ffcbf07 add automation id
Signed-off-by: pengshanyu <yupengshan@hotmail.com>

remove id

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

update id

Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-08-16 16:25:48 -04:00
Yariv Rachmani 9b8708755a Fixing Demo readme
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-08-16 16:23:31 -04:00
Alexander Larsson 71d0f8527c
Merge pull request #501 from pengshanyu/attempts-to-access-forbidden-file-system-resource
Attempts to access forbidden file system resource
2024-08-14 11:38:44 +02:00
pengshanyu 974d764550 check whether access to forbidden file system resource is as expected
Signed-off-by: pengshanyu <yupengshan@hotmail.com>

check whether access to forbidded resources is as expected

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

trim trailing whitespace

Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-08-13 14:28:06 +08:00
Nikolai Sednev acf9b5577d Add patch to main.fmf increased time to 30 min
Signed-off-by: Nikolai Sednev <nsednev@redhat.com>
2024-08-11 07:06:22 -04:00
Nikolai Sednev 0f3e0ccd6d Add code to MR for tcp_max_syn_backlog test
Signed-off-by: Nikolai Sednev <nsednev@redhat.com>
2024-08-09 11:00:01 -04:00
pengshanyu 8252785c78 add Polarion-id
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-08-08 00:09:26 -04:00
pengshanyu cfdfbf097a check /dev/mem is not present in QM partition
Signed-off-by: pengshanyu <yupengshan@hotmail.com>

add a single newline

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

remove -i and -a option

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

change test name

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

use test -e to check if file exists

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

remove output redirection

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

replace hyphen with low-line

Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-08-08 00:09:26 -04:00
Douglas Schilling Landgraf 7d08fe433e ffi: qm-oom-score-adj/test.sh improvement
Received a request to add additional information when the value
do not match for oom-score-adj. Using this opportunity to improve
this test code to have a constant.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-07-31 02:20:25 -04:00
Yariv Rachmani 24b9f4c086 Updating lib/systemd run against non qm image
This PR enables the creation of demo services on non
containerized environment

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-07-30 14:15:25 -04:00
Yariv Rachmani f89236eaad
Merge pull request #496 from nsednev/VROOM-21908
create a test case for setenforce 0 - create polarion TC
2024-07-29 16:13:00 +03:00
nsednev 6ae66a8a3f create a test case for setenforce 0 - create polarion TC
Signed-off-by: nsednev <nsednev@redhat.com>
2024-07-29 08:37:24 -04:00
Yariv Rachmani b5efe519b3
Merge pull request #494 from nsednev/VROOM-19246
Test QM selinux permissions
2024-07-25 15:57:18 +03:00
nsednev 5fe57718e1 Removed irrelevant functions. 2024-07-25 15:17:09 +03:00
Yariv Rachmani aeb7478ad0 Add test for Selinux check_setenforce_fail 2024-07-24 10:00:28 -04:00
Yariv Rachmani 0322896f46
Merge pull request #486 from pengshanyu/add-tier0-test
add tier-0 test case
2024-07-24 13:06:14 +03:00
pengshanyu f1ef96872c remove skip_build
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-07-24 16:22:41 +08:00
pengshanyu 3792942f43 remove PACKIT_COPR_PROJECT
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-07-24 11:43:14 +08:00
pengshanyu 4dfad9c64d add tier-0 test case
Signed-off-by: pengshanyu <yupengshan@hotmail.com>

delete blank Lines

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

trim trailing whitespace

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

update function name and implementation

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

added:check /var on ostree

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

rename old tier-0 to multi-bluechi-agents;rename sanity test to tier-0

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

trailing-whitespace

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

remove old tier 0

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

split sanity test to 6 tests

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

trailing-whitespace

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

not number the tests;add main.fmf;manual_trigger multi-bluechi-agents

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

correct typo

Signed-off-by: pengshanyu <yupengshan@hotmail.com>

add polarion id

Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-07-22 23:52:38 +08:00
Yariv Rachmani 8c509144d1
Merge pull request #492 from rhatdan/selinux
Use pattern and _perms to make policy more recilient
2024-07-21 08:08:23 +03:00
Daniel J Walsh ae27595536
Use pattern and _perms to make policy more recilient
Many times AVC's come in for certain interactions, without all of the
possible AVCs. Changing to use patterns and _perms macros adds common
patterns for allow rules, preventing many expected AVC's.

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2024-07-19 06:41:46 -04:00
Yariv Rachmani 85a8e5b5aa
Merge pull request #490 from aesteve-rh/wayland-new-rules
qm.if: add remaining wayland rules
2024-07-19 13:24:47 +03:00
Yariv Rachmani 2392290295
Merge pull request #460 from Yarboa/packit-fix
test stability changes
2024-07-17 18:14:23 +03:00
Albert Esteve 6e6269d2e0 qm.if: add remaining wayland rules
Add remaining rules required to support
booting and running the wayland scenario,
with a compositor, session creation,
qm dbus management, and all required pieces.

Note that running pem_selinux for creating
the session will be blocked, as it falls back
to unconfined_u with the current rules.

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-07-17 16:33:36 +02:00
Yariv Rachmani e1df9b48c2 TZ update to sync tier-0 testing
remove containers host containers from disk on cleanup
Remove qm.service update referencing to usage of drop-in files
Reorgnizing tests call and definition inside ffi/common/prepare.sh

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-07-17 16:35:03 +03:00
Douglas Schilling Landgraf 7856625a07 devconf: more symbols
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-07-14 11:54:45 -04:00
Douglas Schilling Landgraf 99a00fb014 devconf: use symbol link
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-07-14 11:52:45 -04:00
Douglas Schilling Landgraf a05454f321 demo devconf: initial setup for tests
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-07-14 11:00:18 -04:00
Yariv Rachmani 9ba9ddebf6
Merge pull request #484 from aesteve-rh/wayland
Add SELinux rules for Wayland
2024-07-08 21:08:56 +03:00
Yariv Rachmani 7734f9b162
Merge pull request #485 from aesteve-rh/update-dev-readme
docs: Update devel readme
2024-07-08 16:02:46 +03:00
Albert Esteve d3044cc32d docs: Update devel readme
Update devel README file to reflect
latest updates with sample-images
and automotive-image-builder commands
and project structures.

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-07-08 10:32:40 +02:00
Albert Esteve 72a12c58c6 qm.if: add dbus socket rules
Add SELinux rules to allow a dbus-broker
container to create a QM-specific dbus
socket at the `/run/dbus/` directory.

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-07-08 09:13:50 +02:00
Albert Esteve 64c9bc7952 qm.if: add rules for wayland support
Add minimal set of SELinux rules to allow
running a wayland compositor run as a
container workload inside QM.

In this first iteration, rules assume
using the QM system_bus_socket for the
dbus server. Next step is to allow
a QM-specific dbus daemon to run with
its own session and socket.

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-07-08 09:13:50 +02:00
Yariv Rachmani db67f30bd6
Merge pull request #483 from pengshanyu/group-tests-according-to-network-mode
update agent-flood based on the change of the default Network
2024-07-07 08:51:43 +03:00
pengshanyu 0bf596eaa3 replace qm config file path;exit when other network mode
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-07-05 22:29:44 +08:00
pengshanyu 70650d16a8 updated based on the change of the default Network
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-07-04 13:43:28 +02:00
Sandro Bonazzola edbd6ea940
Merge pull request #482 from sandrobonazzola/gh_action_precommit
Fix again pre-commit dected issues and turn test on for all files
2024-07-04 13:42:07 +02:00
Sandro Bonazzola fdabe3fa08 workflow: always run pre-commit check
- always run pre-commit on all files
- updated actions solving:

```
The following actions uses Node.js version which is deprecated
and will be forced to run on node20: actions/setup-python@v4, actions/checkout@v3.
For more info: https://github.blog/changelog/2024-03-07-github-actions-all-actions-will-run-on-node20-instead-of-node16-by-default/
```

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2024-07-04 11:26:12 +02:00
Sandro Bonazzola ce6a9cf200 Fix missing double quoting in tools/qm-storage-settings
Fixes missing double quotes introduced in #479.
Not detected by pre-commit action as it's not configured
to run on all files.

In tools/qm-storage-settings fix for:
    for STORAGE_CONF_PATH in ${STORAGE_CONF_PATHS[@]}; do
                             ^----------------------^ SC2068 (error): Double quote array expansions to avoid re-splitting elements.

In tools/qm-storage-settings line 52:
        if [ -f ${STORAGE_CONF_PATH} ]; then
                ^------------------^ SC2086 (info): Double quote to prevent globbing and word splitting.

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2024-07-04 10:47:31 +02:00
Yariv Rachmani e2c84c1cb3
Merge pull request #479 from odra/storage-fix
search path for containers/storage.conf
2024-07-04 11:37:31 +03:00
Yariv Rachmani f53bee5cc0
Merge pull request #480 from sandrobonazzola/issue_476
create-seccomp-rules: remove action_type usage
2024-07-04 11:37:01 +03:00
Yariv Rachmani 460c4b524b
Merge pull request #478 from aesteve-rh/fix-syntax
qm.if: fix syntax errors
2024-07-04 10:36:13 +03:00
Sandro Bonazzola d6cf03bb00 create-seccomp-rules: remove action_type usage
Addresses `action_type is referenced but not assigned` error.
Removing action_type usage as suggessted in #476.

Fixes: #476
Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2024-07-04 08:35:06 +02:00
Leonardo Rossetti 6bd9cddf0b
search path for containers/storage.conf
Signed-off-by: Leonardo Rossetti <lrossett@redhat.com>
2024-07-03 14:57:25 -03:00
Sandro Bonazzola 448f8a380a Address pre-commit reported issues
addressed issues reported by pre-commit except:

```
In create-seccomp-rules line 30:
	--arg action "$action_type" \
                      ^----------^ SC2154 (warning): action_type is referenced but not assigned.
```

reported at https://github.com/containers/qm/issues/476

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2024-07-03 09:17:30 -04:00
Albert Esteve 5e5c892332 qm.if: fix syntax errors
Fix syntax errors when running sepolgen-ifgen:
```
/usr/share/selinux/devel/include/services/qm.if: Syntax error on line 398 ) [type=CPAREN]
/usr/share/selinux/devel/include/services/qm.if: Syntax error on line 399 ) [type=CPAREN]
/usr/share/selinux/devel/include/services/qm.if: Syntax error on line 400 ) [type=CPAREN]
/usr/share/selinux/devel/include/services/qm.if: Syntax error on line 558 ' [type=SQUOTE]
/usr/share/selinux/devel/include/services/qm.if: Syntax error on line 621 ) [type=CPAREN]
/usr/share/selinux/devel/include/services/qm.if: Syntax error on line 622 ) [type=CPAREN]
/usr/share/selinux/devel/include/services/qm.if: Syntax error on line 623 ) [type=CPAREN]
```

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-07-03 13:21:17 +02:00
Yariv Rachmani 7f03a18757
Merge pull request #472 from telemaco/disable-hardcoded-oom-score-value-for-testing
tests: Disable oom_score_adj on prepare_test
2024-07-02 22:05:51 +03:00
Daniel J Walsh e44b2ea89f
Merge pull request #474 from sandrobonazzola/pre-commit-update
Update pre-commit config
2024-07-02 05:47:49 -04:00
Daniel J Walsh e776b73854
Merge pull request #475 from sandrobonazzola/markdown-fixes
Fixed markdown lint errors
2024-07-02 05:46:59 -04:00
Roberto Majadas 693fde1636 tests/ffi/disk: Define a custom oom_score_adjust value
Signed-off-by: Roberto Majadas <rmajadas@redhat.com>
2024-07-02 11:36:52 +02:00
Roberto Majadas ef80541768 tests: Allow to tests to define their own qm container custom conf
Signed-off-by: Roberto Majadas <rmajadas@redhat.com>
2024-07-02 11:35:50 +02:00
Sandro Bonazzola 62e86dd2ec Fixed markdown lint errors
Fixed errors reported by markdown linter.

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2024-07-02 11:13:54 +02:00
Sandro Bonazzola 4368f13613 Update pre-commit config
updated pre-commit config to latest versions.

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2024-07-02 10:39:39 +02:00
Roberto Majadas 0068cea5f3 tests: Disable oom_score_adj on prepare_test
The prepare_test fuction overrides the OOMScoreAdjust value. That should
be performed if necessary through systemd drop-in files.

Signed-off-by: Roberto Majadas <rmajadas@redhat.com>
2024-07-01 11:20:16 +02:00
Douglas Schilling Landgraf 0679d5995a release: bump to 0.6.5
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-06-28 02:52:03 -04:00
Daniel J Walsh 90d29cf9a1
Merge pull request #470 from aesteve-rh/remove-ipc-demo-files
selinux: remove ipc-demo file contexts
2024-06-27 11:33:04 -04:00
Albert Esteve 3905d41f64 selinux: remove ipc-demo file contexts
Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-06-27 15:48:05 +02:00
Daniel J Walsh 62c9da7c56
Merge pull request #467 from aesteve-rh/container-ipc-stream-connect
qm.if: allow stream connect for qm_container_ipc_t
2024-06-27 08:03:14 -04:00
Albert Esteve 16ba98d29a qm.if: allow stream connect for qm_container_ipc_t
Solve a connectto issue with ipc socket by calling
`container_stream_connect` macro for the
`qm_container_ipc_t` label.

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-06-27 11:04:16 +02:00
Daniel J Walsh b9d6dddd9e Allow qm_container_ipc_t to use ipc_t sock_files
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2024-06-27 03:02:11 -04:00
Michael Engel 23489208a8 Fixed typo in devel readme
Signed-off-by: Michael Engel <mengel@redhat.com>
2024-06-26 15:09:01 -04:00
Daniel J Walsh 783fe7a78e
Merge pull request #464 from rhatdan/selinux
Attempt to label /run/ipc* content correctly
2024-06-25 11:51:36 -04:00
Daniel J Walsh a7fbb63591
Attempt to label /run/ipc* content correctly
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2024-06-25 09:38:32 -04:00
Yariv Rachmani 4b8f2f09fc
Merge pull request #463 from telemaco/ffi-qm-oom-score-adj-messages
ffi: Add info messages to the qm-omm-score-adj test
2024-06-21 13:08:35 +03:00
Yariv Rachmani b403404aeb
Merge pull request #454 from rhatdan/selinux
Add policy for ipc_t
2024-06-20 19:11:21 +03:00
Daniel J Walsh ef71ff9aeb
Add policy for ipc_t
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2024-06-20 10:42:13 -04:00
Roberto Majadas e26a131d78 ffi: Add info messages to the qm-omm-score-adj test
Signed-off-by: Roberto Majadas <rmajadas@redhat.com>
2024-06-20 10:22:43 +02:00
Yariv Rachmani 6a4c9fdccc
Merge pull request #455 from pengshanyu/add_deny_sched_setattr
add deny_sched_setattr
2024-06-17 10:28:09 +03:00
Yariv Rachmani 8275fc7387
Update tests/ffi/deny_sched_setattr/test.sh
Edit message suggestion
2024-06-16 19:35:31 +03:00
Albert Esteve 7cad7f8901 makefile: build rpms
Add `make rpm` command in order to
run rpmbuild in a handy one-liner.

Configurable through certain env variables.

Signed-off-by: Albert Esteve <aesteve@redhat.com>
2024-06-16 09:01:20 -04:00
pengshanyu 9b890599d8 add Polarion id
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-06-11 10:49:44 +08:00
Douglas Schilling Landgraf d2ac2b3720 tools: generate-release-notes
A tool to generate release notes.

Fixes: https://github.com/containers/qm/issues/457

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-06-08 02:09:30 -04:00
pengshanyu 0455dda5b5 add deny_sched_setattr
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-06-07 12:47:18 +08:00
pengshanyu 19c363c739 add execute_sched_setattr
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-06-03 23:25:37 -04:00
Yariv Rachmani 8f3439b2b5
Merge pull request #449 from weiwang-linda/modprobe_case
ffi: Adding modprobe modules case.
2024-06-02 09:04:17 +03:00
Yariv Rachmani 27a35df239
Merge pull request #448 from weiwang-linda/sysctl
ffi: Adding sysctl test case.
2024-06-02 08:56:43 +03:00
weiwang 48fa529ea0 Add new case for modprobe modules
Check it won't be possible to access /lib/modules to load any module via modprobe inside the QM partition.

Jira-URL: https://issues.redhat.com/browse/VROOM-19336
Signed-off-by: weiwang <weiwang@redhat.com>
2024-06-02 10:26:58 +08:00
weiwang 0a2eb661c9 Add sysctl case for FFI
Test case will execute sysctl inside nested container running on top of QM

Jira-URL: https://issues.redhat.com/browse/VROOM-19309
Signed-off-by: weiwang <weiwang@redhat.com>
2024-06-02 10:20:15 +08:00
Yariv Rachmani 069d85467b
Merge pull request #450 from pengshanyu/add-test_sched_setscheduler
add deny_set_scheduler
2024-06-01 20:37:33 +03:00
pengshanyu 6f5264d2bc use prepare_images and run_container_in_qm
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-05-31 17:44:32 +08:00
pengshanyu b4b76738a1 fix grammatical error
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-05-30 20:34:09 +08:00
pengshanyu 9539498ab9 add variable expected_result
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-05-30 16:00:01 +08:00
pengshanyu 5d2c402181 add deny_set_scheduler
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-05-30 13:50:46 +08:00
Roberto Majadas 3d491af0c8 ffi: Adding qm-omm-score-adj test
Adding a ffi test to validate that que qm container main process runs
with oom_score_adj = 500 and the qm containers processes runs with the
om_score_adj = 750 by default

Signed-off-by: Roberto Majadas <rmajadas@redhat.com>
2024-05-28 14:47:42 -04:00
Daniel J Walsh 5166d3d210
Merge pull request #446 from dougsland/qmdoc
doc: add documentation about OOM Score Adj
2024-05-28 09:00:59 -04:00
Yariv Rachmani ca075b9329
Merge pull request #443 from Yarboa/fix-storge-setup
Fix setup script
2024-05-28 11:02:40 +03:00
Douglas Schilling Landgraf aff4a4a196 doc: add documentation about OOM Score Adj
Fixes: https://github.com/containers/qm/issues/445

See-Also: https://github.com/containers/qm/pull/444

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-28 00:25:57 -04:00
Yariv Rachmani 3a8e56a481 Fix setup script
Also remove gh cli,
it's repo returns 443 lately

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-05-27 19:56:13 +03:00
Lokesh Mandvekar d5a46689a2 Packit: Use podman-next's default repos
This commit switches to using podman-next's default repos so we don't
have to worry about managing targets here.

Signed-off-by: Lokesh Mandvekar <lsm5@redhat.com>
2024-05-22 13:45:08 -04:00
weiwang a63db527a5 FFI test: Add modprobe_module tool
The script will run inside the QM partition. And it won't be possible to access /lib/modules to load any module via modprobe.

Jira-URL: https://issues.redhat.com/browse/VROOM-19336
Signed-off-by: weiwang <weiwang@redhat.com>
2024-05-22 09:13:02 -04:00
pengshanyu 2e577bd399
Merge pull request #438 from pengshanyu/add-tool-test_sched_setscheduler
add tool test_sched_setscheduler
2024-05-17 10:48:45 +08:00
pengshanyu bc87f9ed4e add tool test_sched_setscheduler
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-05-15 16:54:55 +08:00
Douglas Schilling Landgraf 8ada10507e setup: add info regaring usage of setup
This setup script is an unofficial solution designed
to deploy QM in non-automotive environments.

Fixes: https://github.com/containers/qm/issues/430

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-14 10:14:11 -04:00
Douglas Schilling Landgraf c43b56f8c5 release: bump release
Remove the need of moreutils from epel

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-13 23:40:50 -04:00
Douglas Schilling Landgraf 904b572d4b spec: remove the need of moreutils
Fixes: https://github.com/containers/qm/issues/434

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-13 11:13:49 -04:00
Douglas Schilling Landgraf ff4a438f06 main.fmf: agent.flood add test: back
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-12 23:21:53 -04:00
Douglas Schilling Landgraf 1f2cd69ac0 tests: skip agent-flood test
Right now due the change Host=private this test is failing.
Let's skip until we fix it.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-12 23:05:29 -04:00
Douglas Schilling Landgraf 4706e90fc1 docs: devel - add process of copying files to QM
it's possible to copy files into regular images (not ostree based
distros). Let's document it too.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-07 10:03:43 -04:00
Douglas Schilling Landgraf 269026aa95 docs: how to install/remove software in QM
Step by step how to install/remove software in QM
partition.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-07 10:03:43 -04:00
Douglas Schilling Landgraf bc3d5dceb1 doc: add more items to TOC (useful commands)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-07 10:03:43 -04:00
Douglas Schilling Landgraf c078c50f2b packit: add fedora40 to the list
fedora40 was released let's add it to packit.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-04 08:53:29 -04:00
Douglas Schilling Landgraf 2ca0507d37 release v0.6.3
The latest version is out v0.6.3.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-03 23:54:05 -04:00
Douglas Schilling Landgraf 78b899d4fb tools: add qm-storage-settings
setup calls storage() function to execute the initial storage
configuration but it's not called during the ostree deploy as
it's required to call /usr/share/qm/setup. This patch extract
the logic from setup with few improvements and now can be
called externally via ostree / osbuild / osbuild-auto.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-03 23:48:00 -04:00
Douglas Schilling Landgraf af93c7fbbc seccomp: use SYSCALLS_TO_DENY array
This global array can be loaded externally into tools to check
if programs can be added into QM image/yaml that are not allowed
or won't work into the QM partition.

In this case: "sched_setscheduler" and "sched_setattr" which QM
engineers are following the Risk Assessments rules.

Projects like CentOS Automotive Stream Distribution could be take
advanced in the CI/CD pipeline.

Finally, added an example in tool, how could be used in a CI/CD
scenario such integration.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-01 23:57:57 -04:00
Douglas Schilling Landgraf 4c73047cfb docs: Add more info to devel README
Just more useful commands.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-01 10:51:42 -04:00
Douglas Schilling Landgraf 99ce67561f qm.container: change default network option
Change network option to private as default option

Fixes: https://github.com/containers/qm/issues/408

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-01 10:22:42 -04:00
Douglas Schilling Landgraf 5d67b751dc tests: rename README to README.md
Just to show automatically in the web browsers the README
in the right format.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-05-01 09:15:54 -04:00
Douglas Schilling Landgraf fa0cae7bb4 docs: README add RPM mirror info
Provide to users some mirror information where QM packages in different versions (old and newest) can be downloaded for tests and used to compare features.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-30 11:36:25 -04:00
Douglas Schilling Landgraf d25da43960 docs: Add devel README
It's not a trivial road to join the development, let's make
the path easy to everyone that would like to join forces.

Fixes: https://github.com/containers/qm/issues/403
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-29 10:41:56 -04:00
Douglas Schilling Landgraf 625113cb47 qm: make sure remove rootfs when uninstalling
If we created, we must remove it.

Fixes: https://github.com/containers/qm/issues/401
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-29 10:41:33 -04:00
Douglas Schilling Landgraf 3db90a7bdf README: add some commands for selinux help
Got few questions regarding selinux, getting the output
of some debugging tools in hand can save time to everyone.
Let's make it available to users via README.

Fixes: https://github.com/containers/qm/issues/389

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-29 10:41:07 -04:00
Douglas Schilling Landgraf a880645018 prepare.sh: remove FIX-ME regarding restorecon
I cannot reproduce this error, removing fixme.

Fixes: https://github.com/containers/qm/issues/359

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-29 10:40:10 -04:00
Douglas Schilling Landgraf 787dba469c spec: make sure remove speccomp.json
during uninstall make sure to remove the generated speccomp.json

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-27 11:09:35 -04:00
Douglas Schilling Landgraf 7e9e73bec9 setup: add validation for removing PACKAGES_TO_REMOVE
We should validate if the packages exists to avoid exit
in failed command.

Fixes: https://github.com/containers/qm/issues/396

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-27 09:44:12 -04:00
Douglas Schilling Landgraf 528db8233e qm.container: replace tz=local in ostree distro
In recent tests with ostree + quadlet environment the QM service was not able
to work correctly, podman failed to remove /etc/localtime affecting the QM
service. This patch is a workaround to Timezone=local which uses
Environment=TZ to set the default timezone to UTC until we work in root cause.

More information: #367

Fixes: #367

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-26 15:57:41 -04:00
Daniel J Walsh f19543f8f4 Add initial policy type for wayland
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2024-04-26 10:20:15 -04:00
Douglas Schilling Landgraf b81f841167 seccomp: add new tool create-seccomp-rules
This patch removes the logic from setup and creates a independent tool
to manage seccomp rules for QM. It should help with ostree issue.

Fixes: https://github.com/containers/qm/issues/385
Fixes: https://github.com/containers/qm/issues/375

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-25 17:18:12 -04:00
Douglas Schilling Landgraf 0cac7d20f8 spec: remove validation for podman package
podman 5 is shipped already in EL9 platforms.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-24 13:11:40 -04:00
Douglas Schilling Landgraf b7f7cb8d2b tools: add deny_sched_setattr
A tool to test if inside QM it's possible to use the
deny_sched_setattr() syscall to set SCHED_DEADLINE.

Fixes: https://github.com/containers/qm/issues/376

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-24 09:37:25 -04:00
Douglas Schilling Landgraf 1eb55c442b setup: validate qm installation
if users try to run setup without installing QM package we should
exit.

Fixes: https://github.com/containers/qm/issues/364

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-19 07:53:12 -04:00
Douglas Schilling Landgraf 38ce17f331 FFI: add tool test for execute_set_scheduler.c
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-19 07:52:51 -04:00
Douglas Schilling Landgraf 6f58188335 FFI: add setsysctl
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-18 09:58:19 -04:00
Douglas Schilling Landgraf 70eb93e038 qm: add seccomp json also deny sched_setscheduler
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-16 09:06:05 -04:00
Douglas Schilling Landgraf 81e7670442 tests: remove fix-me regarding oom killer
yariv reported that updating kernel resolved the issue.

Fixes: #360

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-10 11:49:31 -04:00
Douglas Schilling Landgraf faf2c07921 qm: add back readonlytmp
Previously we removed the removed the readonlytmp, adding back.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-09 18:45:13 -04:00
Douglas Schilling Landgraf dd311c6b03 qm.container: add back SecurityLabelNested=True
podman recent versions should support it.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-04-09 15:21:57 -04:00
pengshanyu 0c3420a8bd revert to before adding shm
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-03-27 00:42:57 -04:00
Yariv Rachmani a6b2901e39
Merge pull request #352 from pengshanyu/remove-shm-source-code
remove shm souce code
2024-03-26 12:41:44 +02:00
pengshanyu 34b25e23b7 remove shm souce code
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-03-26 11:19:45 +08:00
Yariv Rachmani 468132734d
Merge pull request #349 from pengshanyu/add-shm-to-ffi-tools
add shm to ffi tools
2024-03-18 12:54:17 +02:00
pengshanyu 66c57a78dc add shm to ffi tools
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-03-15 10:21:19 +08:00
Yariv Rachmani 307dff37ca
Merge pull request #347 from pengshanyu/add_autosd_repo_for_c9s
add autosd repo for c9s
2024-03-13 14:18:11 +02:00
pengshanyu 88ce66b119 use template code to install autosd repo;optimize if else;add info message
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-03-13 13:18:27 +08:00
pengshanyu 0253bc966b add autosd repo for c9s
Signed-off-by: pengshanyu <yupengshan@hotmail.com>
2024-03-12 14:35:31 +08:00
Douglas Schilling Landgraf f7a05c2faa tests: fix summary agent-flood/main.fmf
Just replaced summary

Fixes: https://github.com/containers/qm/issues/305

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-02-22 16:11:56 -05:00
Pavol Brilla 0866878c01 Adding test ids to already existing testsA
.fmf files reformatted

Signed-off-by: Pavol Brilla <pbrilla@redhat.com>
2024-02-16 12:55:50 -05:00
Yariv Rachmani 4095073b27 Fixes related to arm64
last fixes after rerunnig on clean arm64
Adding option to run with AutoSD, release repos
Once setting PACKIT_COPR_PROJECT=release

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-02-16 12:55:05 -05:00
Douglas Schilling Landgraf f58cc875dd qm.containers: uncomment DropCapability
Recently we commented DropCapability due crun issue
https://github.com/containers/crun/issues/1388 got resolved.

Fixes: https://github.com/containers/qm/issues/335

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-01-31 10:25:07 -05:00
Yariv Rachmani 3f83ae96fd
Merge pull request #332 from Yarboa/SoC-test-cont
Adding ROOTFS repo dir check
2024-01-29 22:30:38 +02:00
Yariv Rachmani 0f6c591c0c Adding ROOTFS repo dir check
In case QM ${ROOTFS}/etc/yum.repos.d is empty
Add AutoSD repo in order to install QM

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-01-29 17:01:52 +02:00
Yariv Rachmani e6f32bdb7d Adding fixes base on QC SoC
Adding supoort for testing against
SoC HW with distro=centos-stream-automotive-9

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-01-26 14:10:26 -05:00
Daniel J Walsh c6dab9e529 Handle RHEL missing vsomeio packages
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2024-01-25 14:02:14 -05:00
Yariv Rachmani 9885efb580
Merge pull request #327 from mwperina/optional-vsomeip
Make vsomeip dependency optional
2024-01-25 17:51:56 +02:00
Martin Perina e4380f3458 Make vsomeip dependency optional
vsomeip is not available on all required platforms, so if needed we can
pass `with_vsomeip 0` to rpmbuild to disable vsomeip dependency.

Signed-off-by: Martin Perina <mperina@redhat.com>
2024-01-25 12:45:59 +01:00
Yariv Rachmani aa286fd55a
Merge pull request #323 from Yarboa/c9s-rel-gate
Adding epel dependency for packit relase stage
2024-01-23 13:16:41 +02:00
Yariv Rachmani 40d60dac5f Adding epel dependency fir packit relase stage
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-01-23 10:05:37 +02:00
Yariv Rachmani 5c77640c94 Fixing broken gate
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-01-22 10:05:20 -05:00
Douglas Schilling Landgraf 068d25da74 e2e: fix nodename in nodes
With recent changes all nodes generated had node1 as name.

Fixes: https://github.com/containers/qm/issues/301

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-01-19 19:00:47 -05:00
Douglas Schilling Landgraf 7c1e4e7708 e2e: qm-nodes: move NodeName logic to a function
Fixes: https://github.com/containers/qm/issues/316
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-01-19 01:57:52 -05:00
Daniel J Walsh d2e18436d0 Add support for vsomeip3 selinux policy
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-01-17 11:03:32 -05:00
Yariv Rachmani 52bac61d0d Updating recent changes in BluchiConfigurations
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-01-17 10:48:22 -05:00
Yariv Rachmani e4387bc00a Adding setup fix
resolve #310

Current regexp creates malformed podman
storage.conf file for qm, which breaks podman cli inside QM
Adding precommit python fix

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-01-17 10:48:22 -05:00
Douglas Schilling Landgraf cddf8f6e0c qm.container: comment DropCapability
There is errors running podman (OCI permission denied) limiting
the environment. Comment for now.

See-Also: https://github.com/containers/crun/issues/1388

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-01-17 10:09:09 -05:00
Douglas Schilling Landgraf c883d171c2 lib: add python3-dasbus into Container template
Now it's possible to run bluechi stress test

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2024-01-13 17:41:41 -05:00
Yariv Rachmani e2f0c0b11f Add bluechi-agent flood test
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-01-13 00:36:52 -05:00
Yariv Rachmani cb92d2d958 Add configurable Time out before bluechictl list-units qm-agent
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-01-03 09:03:11 -05:00
Yariv Rachmani 5219a0486a Updating old dependency in hirte-agent
hirte-agent -> bluechi-agent
Resolve #293
Adding TMPDIR under [engine]
Updaing tests/e2e/set-ffi-env-e2e
Create full /var directory mounted on different partition

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2024-01-03 09:03:11 -05:00
Yariv Rachmani e8993744d1 Adding support enabeling copr repos for qm
Currently, if packit environment var exist
PACKIT_COPR_PROJECT
Use this copr repo

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-12-22 08:41:36 -05:00
Yariv Rachmani 6ad3a6bae5 Add a fix in setup
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-12-22 08:41:36 -05:00
Yariv Rachmani 3ec382733b Fix current run-test-e2e
Currently tests are not using packit repo created by previous steps
Added an option for scripts --use-qm-copr to be used while running tests with
rhcontainerbot/qm, default is using packit rpms, triggered by scenario=manual parsed in context
scenario == manual

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-12-22 08:41:36 -05:00
Yariv Rachmani 3019b2ef4d Updating test README.md
Update with some more data, related grow mounted filesystem

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-12-12 20:32:43 -05:00
Daniel J Walsh e9b3e04b73
Merge pull request #285 from dougsland/allowed_cpu
move allowedcpu logic to pre-start validation
2023-12-01 16:58:49 -05:00
Douglas Schilling Landgraf aa080c3a77 qm: document systemd drop-in plus QM
The spec file change for AllowedCPU won't affect ostree systems.
This patch will document about using systemd drop-in plus QM.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-30 18:03:02 -05:00
Yariv Rachmani 0b03bda611 ffi test fmf location has changed
Moving test ffi fmf -> /tests/ffi/qm-unit-files
fmf.
Once test discover it calls
/tests/qm-unit-files/test.bash with the relevent env_vars

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-11-28 15:31:45 -05:00
Yariv Rachmani ec074093ad Add new test qm-unit-files
This tests resolved #216

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-11-28 15:31:45 -05:00
Dennis Brendel b9b814b287 FFI: unify memory test sources
There is no need to carry to almost identical source files.

Signed-off-by: Dennis Brendel <dbrendel@redhat.com>
2023-11-27 10:37:06 -05:00
Yariv Rachmani 70350aecdf Adding some debug option to trace mount points and its permissions
Adding unit attribute to support nestes podman exec inside qm

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-11-27 09:30:48 -05:00
Yariv Rachmani 676f1a0a0d Adding nested container fix
Resolve #278

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-11-27 09:30:48 -05:00
Douglas Schilling Landgraf b810de4125 e2e: remove /dev/null for creation of dual network
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-22 18:04:24 -05:00
Daniel J Walsh bdc6b1f564
Merge pull request #276 from Yarboa/autosd-ctr-tests
Fixing tier-1 tests
2023-11-13 10:15:43 -05:00
Yariv Rachmani 219064da9f Remove bash debug
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-11-13 15:23:06 +02:00
Yariv Rachmani 6cd683b7ad Fixing tier-1 tests
Tmt connectivity test fo AutoSD container was broken

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-11-09 15:51:00 +02:00
Yariv Rachmani df395155dd Adding new tests disk-space
Adding test /tests/ffi/disk
The test create partion on /var/qm/ and checks if
non-qm partition / is free with disk space

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-11-07 22:46:31 -05:00
Daniel J Walsh ca716924d6
Merge pull request #275 from dougsland/quadlet
e2e: replace systemd stubs with quadlet
2023-11-07 07:24:41 -05:00
Douglas Schilling Landgraf e4cf422ecf e2e: replace systemd stubs with quadlet
podman generating systemd services is deprecated.
This patch uses quadlet container file to reproduce
an auto environment in a nested container.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-06 21:46:02 -05:00
Douglas Schilling Landgraf 43075c3f2d setup: remove vim and findutils
Reduce the attack surface, for tests we can create a different
mechanism to install the packages.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-06 09:47:17 -05:00
Douglas Schilling Landgraf c906ab2a9e release: 0.6.0
Let's ship a new QM with all fresh changes.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-05 07:59:49 -05:00
Douglas Schilling Landgraf a3815b5862 setup: add findutils to include find tool
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-04 22:45:09 -04:00
Daniel J Walsh 30de9ff16b
Merge pull request #269 from dougsland/vim
setup: add vim
2023-11-03 17:16:25 -04:00
Douglas Schilling Landgraf 955e8b539b release: 0.5.9
Create a new release with additional features added.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-03 15:58:20 -04:00
Douglas Schilling Landgraf e0198dc1a8 setup: add vim
add vim editor to the qm container

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-03 13:47:10 -04:00
Douglas Schilling Landgraf ee005daa89 setup: make sure we have iptables-nft
RHEL kernel uses iptables-nft, not iptables-legacy.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-03 13:34:54 -04:00
Douglas Schilling Landgraf b67fe3ea42 e2e: add iptables-nft to control/nodeX nodes
To avoid container startup issues with iptables legacy let's make sure
control and node1 contain iptables-nft.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-02 18:51:48 -04:00
Douglas Schilling Landgraf 8a0c66c495 e2e: always update ManagerHost
We had cases where ManagerHost in node{ID} is not updated with what qm container contain as ManagerHost. This happens as the ContainerFile.node can be generated days/hours/minutes before the qm container be in fact created.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-01 18:47:37 -04:00
Douglas Schilling Landgraf f1ee3169b6 e2e: improve cleanup call
now cleanup dualnetwork stack

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-01 12:29:47 -04:00
Yariv Rachmani 985b0340f9 Added some error catch mechanism
Add the following based on PR review

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-11-01 10:41:58 -04:00
Yariv Rachmani 0b5778c18e Adding FFI memeory test
Adding tmt FFI plan running ffi tests
Prepare script per images,
c9s, fedora, autosd (vm)
followed by test running cotainer and verify systemd activated oom killer

Adding supoport in OS based prepares
Tmt tests requires, to use tmt --context with scenario=ffi, distro=<os type> run ..

ffi-tools container image is downloaded from sig container-images

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-11-01 10:41:58 -04:00
Douglas Schilling Landgraf 57fb04cc22 release: increase version for 0.5.8
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-11-01 09:38:02 -04:00
Douglas Schilling Landgraf 24a8580f33 e2e: use 1> /dev/null to get errors msgs
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-10-31 23:24:54 -04:00
Yariv Rachmani c9d57e4592 Update bluchi repo to centos-auto-sig
Resolve #257

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-26 16:19:26 -04:00
Yariv Rachmani 948d09a2e6 Fix issue #255
This PR fix skipped corrections

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-26 15:47:34 -04:00
Douglas Schilling Landgraf 8afcc1b21d e2e: adjust the path for controller.conf
Currently, e2e is failing with timeout as the AllowedNames is not
set correctly.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-10-26 14:48:59 -04:00
Yariv Rachmani bdaf7c00a0
Merge pull request #254 from Yarboa/fix-cte-file
Fix ContainerFile.template errors
2023-10-24 14:18:57 +03:00
Yariv Rachmani 2c44560298 Fix ContainerFile.template errors
CI started to FAIL on dnf install
Unable to find a match: tmt-report-junit, removed it for now

Remove the curl configuration of bluechi entities

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-24 11:12:41 +03:00
Yariv Rachmani e5698e3c71 Set testing infra for ffi
resolves partly #233
The following setup script, set identical deploy topology for:
AutoSD.qcow2 image
autosd container
c9s

FFI tests run against unified test topology.
Adding FFI plan/e2e
install qm env inside c9s host and run qm-connectivity through
ffi filter

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-18 13:14:05 -04:00
Yariv Rachmani bc473f434c Apply changes of bluechi configs in e2e containers
e2e tier-0 started to fail probably due to updates in Bluechi
Configuration files
Updating cinfig files in e2e tests setup

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-18 09:58:10 -04:00
Yariv Rachmani 6fce5754cc Fixing location of agent.conf
moving from /etc/bluechi/agent.conf ->
     /etc/bluechi/bluechi/agent.conf.d/

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-17 15:20:50 -04:00
Yariv Rachmani d7ece83425 Remove tier-1 test
Resolve #250

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-17 15:19:34 -04:00
Daniel J Walsh bbd92d753d
Merge pull request #246 from rhatdan/selinux1
Fix up latest qm AVCs
2023-10-16 12:41:24 -04:00
Daniel J Walsh d4b6d37498
Merge pull request #247 from Yarboa/add-codeowners
Adding odra to CodeOwners
2023-10-16 12:39:49 -04:00
Yariv Rachmani 6ffbf839cb Adding odra to CodeOwners
odra AKA lrossetti

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-16 19:03:26 +03:00
Daniel J Walsh ae9fad3086
Fix up latest qm AVCs
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-10-16 09:37:00 -04:00
Paul Wallrabe 8a5fb8ca55 Update README.md
Signed-off-by: Paul Wallrabe <code@raballew.de>
2023-10-12 15:02:00 -04:00
Yariv Rachmani 0e2899c457 Introducing new tmt plans directory
Maintianing the following tree for tests visibility
qm
 |-tests
 |-plans

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-11 09:54:51 -04:00
Yariv Rachmani b2cea2f9e1 Add CI test verify Quay AutoSD QM is working
Resolves #236

Add tier-1 to packit plans
Currently autosd container is running with --privileged
Test tier-1 will fail due to bug in qm #238

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-10 09:39:08 -04:00
Douglas Schilling Landgraf d694727108 ffi: add generated bin/ for the tools in gitignore
gcc will generat some files, let's ignore the generated bin dir.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-10-10 09:37:35 -04:00
Douglas Schilling Landgraf 9303f9ec8e ffi: fix makefile for file-allocate
the make all was failing. this fix the issue.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-10-10 09:37:35 -04:00
Yariv Rachmani 625b391efb Adding Makefile for ffi-tools container
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-09 17:57:59 -04:00
Yariv Rachmani 32f42cca82
Merge pull request #238 from odra/fix-setup-hostname
fix using skip-systemctl with other options
2023-10-10 00:09:24 +03:00
Leonardo Rossetti 445d496d8b
fix e2e param
Signed-off-by: Leonardo Rossetti <lrossett@redhat.com>
2023-10-09 17:52:50 -03:00
Leonardo Rossetti 4e32144bbd
print agent hostname
Signed-off-by: Leonardo Rossetti <lrossett@redhat.com>
2023-10-09 17:26:33 -03:00
Leonardo Rossetti ad256dd525
fix using skip-systemctl with other options
Signed-off-by: Leonardo Rossetti <lrossett@redhat.com>
2023-10-09 17:16:53 -03:00
Yariv Rachmani cfbce8d09a Review changes
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-04 09:12:56 -04:00
Yariv Rachmani 3167e6ede1 fix e2e
Resolves #226
Systemd is not installed under /usr/lib/qm/rootfs
during  create_qm container
qm is failing since no /sbin/init created under /usr/lib/qm/rootfs

adding cap-add SYS_ADMIN capability for build of nodeX

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-10-04 09:12:56 -04:00
Yariv Rachmani 27fb454f43 Update nodeX container file
Based on latest changes
This resolves #226

qm.service failes to load
ignoring: unsupported key 'SecurityLabelNested' in group 'Container'

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-29 11:21:45 -04:00
Douglas Schilling Landgraf 5ab7719750 e2e: add packages to build podman
Fixes: https://github.com/containers/qm/issues/227

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-28 11:07:16 -04:00
Douglas Schilling Landgraf 151f842910 setup: add rwetcfs rwvarfs skip-systemctl to list
Fixes: https://github.com/containers/qm/issues/225

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-28 10:53:44 -04:00
Douglas Schilling Landgraf faf67595af setup: make sure create rootfs req dirs
Fixes: https://github.com/containers/qm/issues/223

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-28 10:53:44 -04:00
Douglas Schilling Landgraf a378056b9a e2e: fix bash complain about missing []
Fixes: https://github.com/containers/qm/issues/219

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-27 11:25:38 -04:00
Daniel J Walsh 715bbf8cb3 Change qm to use /var/qm and /etc/qm for writable directories in qm
This will help work with ostree systemd with read-only /usr partitions.

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-09-27 10:24:12 -04:00
Dennis Brendel 6e3d03b6d4 tests/e2e/lib/utils: fix spaces vs tabs
Signed-off-by: Dennis Brendel <dbrendel@redhat.com>
2023-09-26 09:43:08 -04:00
Dennis Brendel 39c200eabd tests/e2e/lib/systemd: fix spaces vs tabs
Signed-off-by: Dennis Brendel <dbrendel@redhat.com>
2023-09-26 09:43:08 -04:00
Dennis Brendel e0d5da2c36 tests/e2e/lib/container: make variables local
This keeps the namespace clean and prevents conflicts.

Signed-off-by: Dennis Brendel <dbrendel@redhat.com>
2023-09-26 09:43:08 -04:00
Dennis Brendel f4f51610a7 tests/e2e/lib/container: use only spaces for indentation
This fixes the mixture of tabs and spaces.

Signed-off-by: Dennis Brendel <dbrendel@redhat.com>
2023-09-26 09:43:08 -04:00
Dennis Brendel db85eeb51e tests/e2e/run-test-e2e: remove not needed bashism
Signed-off-by: Dennis Brendel <dbrendel@redhat.com>
2023-09-26 09:43:08 -04:00
Dennis Brendel de37beb5f9 tests/e2e/run-test-e2e: improve colored output handling
Only color if the terminal has support for that, and use variables
instead of using the control sequence everywhere.

Signed-off-by: Dennis Brendel <dbrendel@redhat.com>
2023-09-26 09:43:08 -04:00
Dennis Brendel e47d560850 tests/e2e/run-test-e2e: add missing backslash in the help message
Signed-off-by: Dennis Brendel <dbrendel@redhat.com>
2023-09-26 09:43:08 -04:00
Dennis Brendel 278bd14dba tests/e2e/run-test-e2e: use heredoc for help message
This improves readability by a lot.

Signed-off-by: Dennis Brendel <dbrendel@redhat.com>
2023-09-26 09:43:08 -04:00
Dennis Brendel d1e6e0eab2 tests/e2e/run-test-e2e: cleanup indentation
There was some mixup of spaces and tabs, I transformed them all into
tabs and aligned the indentation to be 4 spaces per level, which is what
most of the file followed.

Signed-off-by: Dennis Brendel <dbrendel@redhat.com>
2023-09-26 09:43:08 -04:00
Daniel J Walsh 44da37e34c
Merge pull request #215 from Yarboa/bluchi-updates
Fix due to renaming of bluechid to controller
2023-09-21 07:48:41 -04:00
Yariv Rachmani 230e5d74a3 Fix due to renaming of bluechid to controller
Bluechid configuration files renamed from
bluechi.cong -> controller.conf
Updates scripts and Container files based on that

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-09-21 13:32:32 +03:00
Douglas Schilling Landgraf e88fe4ff0b Add support to FFI
Just an initial code for FFI:

- Add C sources to eat memory (ASIL: 20) (QM: 90)
- file-allocate source

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-18 18:56:18 -04:00
Daniel J Walsh ea6b11417a
Merge pull request #211 from Yarboa/add-reviewers
Adding Dennis as default reviewer
2023-09-18 16:07:47 -04:00
Yariv Rachmani 5f95e5b9a8 Adding Dennis & Priyanka
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-09-18 18:30:20 +03:00
Yariv Rachmani 48948a3e5d Updating with latest fixes based on AutoSD verification
README contains:
- AutoSD tmt command line example
- \-c distro while runnign againse CentOS stream
(packit tests already run with packit with this parameter)
- Environment variables in case of different qm and containers names

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-09-18 10:55:28 -04:00
Yariv Rachmani 1d85b25458 Updating tests to work against qm AutoSD image
The test run prepare step only on c9s and fedora
ENV variables changed based on the distro it is inquire

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-09-18 10:55:28 -04:00
Daniel J Walsh 94998b55c9 limit the number of processes/tasks inside of the QM
The default limit on number of processes within the container is 2048.
This is far too low for QM. Selecting 50% of max seems like a better number
but really this needs to be set by the final distributor of the OS.

Also set the maximum number of open file descriptors.

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-09-12 20:10:38 -04:00
Yariv Rachmani 1e7bf2a395 Setting ImageID once image created for the first time
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-09-11 15:29:25 -04:00
Yariv Rachmani ed396f59d3 Running single container for nodes and controllers
Resolve https://github.com/containers/qm/issues/164
nodeX images

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-09-11 15:29:25 -04:00
Leonardo Rossetti c411591101 using chroot to link systemd service
Signed-off-by: Leonardo Rossetti <lrossett@redhat.com>
2023-09-07 13:32:10 -04:00
Daniel J Walsh 0f4e1332a9
Merge pull request #201 from dougsland/dashboard
car-dashboard: fix typo
2023-09-07 11:15:45 -04:00
Douglas Schilling Landgraf 608412509f car-dashboard: fix typo
hail -> rail

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-07 09:56:30 -04:00
Daniel J Walsh e9d8646401 Allow qm_containers to sendo qm_t unix_domain_sockets
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-09-07 07:56:16 -04:00
Douglas Schilling Landgraf b953c4f735 e2e: Add dbus-devel package
dbus-devel provides libraries and header files needed for developing
software that uses D-BUS.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-05 18:19:22 -04:00
Douglas Schilling Landgraf 603eb93f9b e2e: add markdown-cli linter
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-05 09:50:47 -04:00
Douglas Schilling Landgraf 0a7c7afd14 e2e: add rust support
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-03 08:00:07 -04:00
Douglas Schilling Landgraf ad07470515 e2e: add ruby to the containers image
Fixes: https://github.com/containers/qm/issues/195

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-02 02:00:25 -04:00
Douglas Schilling Landgraf a79218217b release: bump to 0.5.6
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-01 18:02:13 -04:00
Douglas Schilling Landgraf 8c1282bd05 build: adjust make to handle floats in os-release
The script was failing when getting "9.2" in VERSION_ID.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-09-01 17:45:39 -04:00
Douglas Schilling Landgraf 31dd114d7c e2e: add go-toolset
go-toolset provides the Go programming language tools and libraries.

Fixes: https://github.com/containers/qm/issues/191

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-31 22:35:47 -04:00
Douglas Schilling Landgraf d8478d4a12 version: bump release to match 0.5.5
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-30 17:23:22 -04:00
Douglas Landgraf faed96d984 Update .packit.yaml
should not be needed to require rpkg

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-30 14:12:41 -04:00
Douglas Schilling Landgraf 55b493d5a8 makefile: change $$NAME to $$ID and add autosd
Fixes: https://github.com/containers/qm/issues/177

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-30 13:45:40 -04:00
Douglas Schilling Landgraf f64e83098a demos: add copr for bluechi
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-30 11:49:06 -04:00
Leonardo Rossetti e4733b48c4 enable rootfs bluechi-agent
Signed-off-by: Leonardo Rossetti <lrossett@redhat.com>
2023-08-29 19:43:53 -04:00
Leonardo Rossetti a6920550f8 add --hostname option to qm/setup
Signed-off-by: Leonardo Rossetti <lrossett@redhat.com>
2023-08-29 19:43:53 -04:00
Douglas Schilling Landgraf f04d10e033 bump release to fix qm.spec
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-29 14:33:57 -04:00
Douglas Landgraf b53424fb76 Update qm.spec
bluechi doesn't exist. The rename should happen soon. Getting back to hirte.
2023-08-29 14:05:56 -04:00
Leonardo Rossetti f206278ef6 fixing --skip-systemctl param
Signed-off-by: Leonardo Rossetti <lrossett@redhat.com>
2023-08-29 09:37:11 -04:00
Douglas Schilling Landgraf b41dd9a6e2 version: update the version with the last release
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-28 19:29:56 -04:00
Leonardo Rossetti 9ef2f789b4 SYSTEMCTL_SKIP env var
Signed-off-by: Leonardo Rossetti <lrossett@redhat.com>
2023-08-28 16:55:32 -04:00
Douglas Landgraf 252412540b Update VERSION
Set version to a new release.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-28 11:49:39 -04:00
Sandro Bonazzola dd5bf23f3e Align version with latest tag
Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-08-23 10:35:21 -04:00
Douglas Schilling Landgraf 33e5edd3bb rename hirte to bluechi
Hirte project has being renamed to BlueChi.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-22 09:11:26 -04:00
Douglas Schilling Landgraf 2f2a453d4d e2e: add pcp package
Performance Co-Pilot (PCP) provides a framework and services to support system-level performance monitoring and performance management. Useful for development and testing.

Fixes: https://github.com/containers/qm/issues/174

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-21 11:44:48 -04:00
Douglas Schilling Landgraf 5c9d4ba726 e2e: add pre-commit tool to validate code
pre-commit has several validations that can be used
during development.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-19 15:55:53 -04:00
Douglas Schilling Landgraf f3777694c1 e2e: add more tools for development
- ShellCheck: validate sh scripts
- python8-flake: add flake8 tool

Additionally, replaced some spaces with tabs.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-19 14:16:05 -04:00
Daniel J Walsh c8a00601dc
Merge pull request #170 from lsm5/packit-target-update
Packit: Enable fedora-39 targets and bodhi for epel-9
2023-08-18 05:34:31 -04:00
Lokesh Mandvekar fe151fadce
Packit: Enable fedora-39 targets and bodhi for epel-9
Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-08-17 11:12:39 -04:00
Daniel J Walsh f48969a9e0 Allow qm containers to read/execute qm_file_t content
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-08-16 11:20:03 -04:00
Daniel J Walsh 8029307582
Merge pull request #167 from dougsland/add-packages
e2e: add more packages as requirement
2023-08-15 14:38:07 -04:00
Douglas Schilling Landgraf a14d3b8476 e2e: add gh tool
The e2e tool is much more than E2E these days. It helps
development and tests, so having everyting in AllInOne
solution make things faster and quicker.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-15 14:45:31 +00:00
Douglas Schilling Landgraf b0f502c6af e2e: add more packages as requirement
lcov - required for bluechi for doc generation
g++ - required for bluechi
fpaste - easy to share logs

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-15 14:17:26 +00:00
Douglas Schilling Landgraf b4cfb630d3 e2e: add packages for tmt development
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-12 00:57:56 -04:00
Daniel J Walsh dd9545af1c Allow qm_t to use sys_nice capability
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-08-10 21:50:39 -04:00
Douglas Schilling Landgraf edcd9c7696 e2e: add days and hours for the e2e tests measure
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-08 16:14:33 -04:00
Martin Pitt 7d9f9db0b2
packit: Restore podman-next target list (#162)
I removed them in commit 62c1ee9f17 with ignoring that this is a
deliberate subset of targets, as this project doesn't build in e.g.
Fedora 37 or C8S. Put them back.

Signed-off-by: Martin Pitt <mpitt@redhat.com>
2023-08-08 14:08:34 -04:00
Douglas Schilling Landgraf 32eba5752d e2e: add more info regarding the tests
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-08 09:49:24 -04:00
Martin Pitt 62c1ee9f17
packit: Build PRs into default packit COPRs (#160)
* packit: Drop explicit target lists for rhcontainerbot COPRs

If they differ from the actually configured target list in the COPR, the
build will either fail (if the packit user wasn't granted admin rights), or
actually reconfigure the COPR -- neither is desirable.

Specifying the target list is not necessary any more since
https://github.com/packit/packit-service/issues/1499 got fixed.

Signed-off-by: Martin Pitt <martin@piware.de>

* packit: Build PRs into default packit COPRs

Building all PRs of all container projects into the same COPR does not
properly isolate PRs from each other.

To avoid that, change the copr_build configuration to use the packit
default COPRs, which are specific to the particular PR, and disappear
after a few weeks. Depending projects should only run against what
landed in qm/main i.e. the podman-next COPR.

Signed-off-by: Martin Pitt <mpitt@redhat.com>

---------

Signed-off-by: Martin Pitt <martin@piware.de>
Signed-off-by: Martin Pitt <mpitt@redhat.com>
2023-08-08 09:04:41 -04:00
Daniel J Walsh a44f687e42
Merge pull request #158 from sandrobonazzola/missing_containers-common
partially revert commit 1cfd978
2023-08-08 08:08:44 -04:00
Sandro Bonazzola befec14909 partially revert commit 1cfd978
partially reverts commit 1cfd978 not requiring podman > 4.5 only on RHEL
as it's available in CentOS Stream 9.
Requiring hirte-agent everywhere as it's available in EPEL 9.

Fixes #146

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-08-08 10:53:29 +02:00
Douglas Schilling Landgraf 67dfef1ea5 e2e: add tool remove-containers.sh
remove all containers/image which name start with node*
or control from the output of podman ps. Useful to cleanup
environments before measures.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-07 23:19:49 -04:00
Douglas Schilling Landgraf 2b6279673a e2e: list only services created by the test script
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-07 14:05:24 -04:00
Douglas Schilling Landgraf 094501962e e2e: handle multiline in hirte.conf
Hirte has the maximum length per line in the configuration.
The limit is 500 or use the multiline approach for long lines.

More info:
https://github.com/containers/hirte/blob/main/doc/docs/configuration.md#maximum-line-length

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-07 10:38:41 -04:00
Douglas Schilling Landgraf ac84d0ccf1 e2e: create systemd stub srv in all qm nodes
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-06 18:41:13 -04:00
Douglas Schilling Landgraf 2895fc021a e2e: ignore some outputs
- the network creation can show an error like "network already exists"
- sysctl stdin output can be ignored as well

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-06 17:19:02 -04:00
Yariv Rachmani 33d07eb065
Merge pull request #150 from dougsland/owners
CODEOWNERS: Yariv and Sandro
2023-08-06 10:17:02 +03:00
Douglas Schilling Landgraf dabcf22b78 e2e: run-test-e2e improve cleanup
Now remove all containers dynamic created.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-05 22:41:29 -04:00
Douglas Schilling Landgraf 762b0ef948 e2e: update lib/container to add node'N' nodes
Now that we have a ability to create 'N' nodes
we need to add it to AllowedNodeNames too.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-05 16:23:48 -04:00
Douglas Schilling Landgraf 1532ac0e16 e2e: run-test-e2e add --number-of-nodes
To test hirte and qm in scale we will need a way to easily
create 'N' nodes.

Example for creating 8 nodes with 8 qm containers inside:
   ./run-test-e2e --number-of-node=8

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-05 15:27:33 -04:00
Douglas Schilling Landgraf e2d0089a98 CODEOWNERS: adding Yarboa and Sandro
- Yarboa has being helping us in the QE side
- Sandro has being helping us in the tests for the virtualization platform
  and fedora packaging

Both understand and uses QM in different ways, if possible,
i would like to add them as owners and reviwers of the code
to keep our quality high.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-05 15:24:13 -04:00
Douglas Schilling Landgraf a8ce78aabc e2e: remove commented line in the AllowedNodeNames
In this moment of the deploy, this option is not commented. Fixing the sed.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-08-05 14:24:34 -04:00
Daniel J Walsh 8c8cce3758
Allow qm container domains additional access (#144)
Allow qm containers to search through qm_file_t directories.
Allow qm containers to search through sysfs file system directories.

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-08-03 10:58:00 -04:00
Sandro Bonazzola 7464e9c1eb
spec: target /usr/lib for qm module (#145)
Fixes #142

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-08-03 08:25:13 -04:00
Douglas Schilling Landgraf 0c5b515914 e2e: update doc for tmt locally
Minor changes to improve the doc.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-07-31 09:54:11 -04:00
Daniel J Walsh 391f67acc6
Merge pull request #140 from dougsland/docs
docs: Adding docs/quadlet-examples dir
2023-07-29 06:15:52 -04:00
Douglas Schilling Landgraf 7eb86d7bd0 docs: Adding docs/quadlet-examples dir
Initial commit provided by Dan Walsh running android container
on top of kvm + wayland.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-07-28 17:50:05 +00:00
Douglas Schilling Landgraf adaec344c6 spec: remove errors in the spec
Nothing bad but let's remove the errors from rpmlint

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-07-28 12:36:45 -04:00
Douglas Schilling Landgraf 97b6f573ed demo: improvements
- check errors in commands
- auto add node names into hirte config
- general improvements in the demo script

Resolves: https://github.com/containers/qm/issues/103

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-07-28 12:08:01 -04:00
Sandro Bonazzola 96fb7a7ce5 README: add instructions for build deps
Follow up on https://github.com/containers/qm/pull/122
review.
Adding instructions for enabling CRB repository on CS9.

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-07-27 10:39:30 -04:00
Sandro Bonazzola d309aa7611 spec: require golang-github-cpuguy83-md2man
explicitly require `golang-github-cpuguy83-md2man` instead of
`%{_bindir}/go-md2man` and added a note about where to find it
on CentOS Stream 9.

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-07-27 10:39:30 -04:00
Douglas Landgraf 1e18ef145e
qm.container: remove ExecuteStartPre (#133)
It's not used at all.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-07-26 16:10:01 -04:00
Yariv Rachmani 9e2a056224
Fix hirtectl config (#131)
During inspection of systemctl start qm failures
It seems that config files were not set properly due to
regexp inaccuracies

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-07-26 13:23:47 -04:00
Douglas Landgraf b923838dfd
qm: improve qm and setup (#127)
- demo: validate if commands exists
- e2e: add sudo command to template file
- getopt(), now users can use --installdir and --rootfs
- --help and usage message
- added root_check()
- constants
- use of bash to include array type
- demo: rename asilservice.py

Resolves: https://github.com/containers/qm/issues/114

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-07-25 13:29:58 -04:00
Yariv Rachmani a54acf1469
Adding how to test manually (#126)
Adding section to tests/e2e/README.md how run test locally

Signed-off-by: Yarboa <yrachman@redhat.com>
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-07-24 23:27:38 -04:00
Lokesh Mandvekar 958a2d7fea
RPM: autospec macros not defined yet in EL9 (#124)
Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-07-21 11:56:50 -04:00
Douglas Landgraf 83fc1e6335
tests: fix pre-commit warnings in bash/python (#125)
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-07-21 11:42:15 -04:00
Daniel J Walsh 03f2d6c5d4
Default timezone to local to match the hosts (#117)
Fixes: https://github.com/containers/qm/issues/113

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-07-20 08:41:25 -04:00
Yariv Rachmani 2eb0e10135
Fix linting issue (#119)
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-07-20 08:21:13 -04:00
Sandro Bonazzola 1cf6b9937d
stop qm.service only on real install (#116)
* stop qm.service only on real install

previously qm.service was stopped always, including when reconfiguring
hirte-agent at qm.service start.

Now qm.service is stopped only if a real install is being executed.

Fixes #106

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-07-19 11:41:24 -04:00
Douglas Landgraf 4a5cfef43b
Merge pull request #115 from sandrobonazzola/fix_105
start qm.service at boot
2023-07-19 09:15:50 -04:00
Sandro Bonazzola 7b38b904ce start qm.service at boot
Added Install section as per
https://docs.podman.io/en/latest/markdown/podman-systemd.unit.5.html
in order to get the container up after reboot.

Fixes #105

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-07-19 11:54:19 +02:00
Douglas Landgraf 147b041c75
Merge pull request #111 from sandrobonazzola/qm-connect-fixes
fix connectivity test shellcheck
2023-07-17 09:30:15 -04:00
Douglas Landgraf 6a7af260f1
Merge pull request #107 from sandrobonazzola/setup_fix
make setup pass shellcheck
2023-07-17 09:29:26 -04:00
Douglas Landgraf 34b9eb0d5f
Merge pull request #108 from sandrobonazzola/update-spec-version
update-spec-version.sh shellcheck fixes
2023-07-17 09:28:39 -04:00
Douglas Landgraf 3a3a79e5bb
Merge pull request #109 from sandrobonazzola/markdown_fix
markdown: make it pass markdownlint
2023-07-17 09:27:58 -04:00
Douglas Landgraf ec0b33a357
Merge pull request #110 from sandrobonazzola/packit
make .packit.sh pass shellcheck
2023-07-17 09:27:00 -04:00
Sandro Bonazzola addfca3665 fix connectivity test shellcheck
fixed issues detected by shellcheck on qm connectivity test.

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-07-17 14:10:49 +02:00
Sandro Bonazzola 33825b29d8 make .packit.sh pass shellcheck
Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-07-17 13:52:37 +02:00
Sandro Bonazzola 76c435b0d8 markdown: make it pass markdownlint
Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-07-17 12:32:31 +02:00
Sandro Bonazzola 817ed77ac0 update-spec-version.sh shellcheck fixes
make shellcheck pass on update-spec-version.sh

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-07-17 11:44:15 +02:00
Sandro Bonazzola 6169713128 make setup pass shellcheck
pre-commit hook requires to pass shellcheck but existing code
didn't pass the test.

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-07-17 11:19:59 +02:00
Douglas Landgraf 504e8048c0
Merge pull request #102 from sandrobonazzola/patch-1
Fix #101
2023-07-14 09:01:21 -04:00
Sandro Bonazzola 0484af3d2f Fix #101
Fixed a typo in `qm.container` causing systemd to report
`Unknown key name 'ExecPreStart' in section 'Service', ignoring`.

Fixes #101

Signed-off-by: Sandro Bonazzola <sbonazzo@redhat.com>
2023-07-14 10:57:39 +02:00
Daniel J Walsh 85b2ffbb9f
Merge pull request #100 from containers/adjust_spec
Make %ghost own the file created in %post
2023-07-10 16:19:27 -04:00
Pierre-Yves Chibon 4694d9bdda Make %ghost own the file created in %post
Otherwise we end up with a file in /etc/containers/systemd that
isn't linked in the RPM database to the qm package making people
wonder where this is coming from.

Signed-off-by: Pierre-Yves Chibon <pingou@pingoured.fr>
2023-07-07 12:16:29 +02:00
Eric Curtin 9a12a0268d
Minor typo (#99)
cgoups to cgroups, just something I noticed while giving a quick read.

Signed-off-by: Eric Curtin <ecurtin@redhat.com>
2023-07-06 08:54:55 -04:00
Daniel J Walsh 51b3aa04fb
Merge pull request #97 from dougsland/dual
e2e: add dual stack support
2023-06-26 16:50:09 -04:00
Douglas Schilling Landgraf 80e65fed8f e2e: add dual stack support
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-06-26 13:34:18 -04:00
Douglas Landgraf 97a4ce5c65
make: add validation for rhel9 or lower (#94)
* make: add validation for rhel9 or lower

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

* spec: remove cond for user_namespace

Should be addressed by Makefile

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>

---------

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-06-23 09:46:39 -04:00
Daniel J Walsh c3332121c5
Merge pull request #96 from lsm5/rhel-user-namespace
RPM: ensure user_namespace removed only on rhel9
2023-06-23 05:32:02 -04:00
Lokesh Mandvekar e15da9476a
RPM: ensure user_namespace removed only on rhel9
Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-06-22 14:17:01 -04:00
Daniel J Walsh f0b2123840
Merge pull request #93 from lsm5/ci-test
RPM: remove `user_namespace` for c9s in qm.spec
2023-06-22 05:58:06 -04:00
Lokesh Mandvekar 6110b1bfea
RPM: remove `user_namespace` for c9s in qm.spec
Copr builds occur in a mock chroot on a Fedora host. So Makefile checks
for /sys/fs/selinux/class/user_namespace may suffice for local builds on
c9s, but won't work alone for Copr builds.

This patch will remove `user_namespace` from qm.if for all c9s/rhel
environments.

Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-06-15 12:33:21 -04:00
Douglas Landgraf 68a58a757d
Merge pull request #88 from dougsland/e2ereadme
e2e: fix README.md
2023-06-12 01:13:35 -04:00
Douglas Schilling Landgraf a223eb58ac e2e: fix README.md
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-06-12 01:11:55 -04:00
Douglas Landgraf 4b3c95c45b
Merge pull request #86 from dougsland/podmandualstack
systemd: fix bash errors
2023-06-12 01:06:04 -04:00
Douglas Schilling Landgraf 5d7dc959c9 systemd: fix bash errors
Just found these errors executing dualstack tests.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-06-12 00:52:26 -04:00
Douglas Landgraf a503df3cce
Merge pull request #83 from dougsland/templatepr
template: add more python packages and link
2023-06-11 15:14:06 -04:00
Douglas Schilling Landgraf 58cfcc0625 template: add vim-enhanced
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-06-11 14:47:15 -04:00
Douglas Schilling Landgraf c293cec773 template: add more python packages and link
Adds:

- python3-gobject, python3-pip
- alias from python3 to python

Resolves:
https://github.com/containers/qm/issues/78
https://github.com/containers/qm/issues/71

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-06-11 14:34:47 -04:00
Douglas Landgraf 9124842a8a
Merge pull request #82 from Yarboa/PR_77
Pr_77
2023-06-08 10:09:52 -04:00
Yariv Rachmani 27ad740ec0 Adding wait mechanism for containers
Currently test is failing since the container-safety.service
Is booting slow

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-06-08 15:39:51 +03:00
Aditya Kode f15955a948 Create ContainerFile.template
Adding the Fix for container location

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-06-08 15:39:03 +03:00
Aditya Kode 53b2511170 Changed ContainerFile.control to ContainerFile.template
Signed-off-by: Aditya Kode <aditya.kode21@pccoepune.org>
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-06-07 16:40:24 +03:00
Yariv Rachmani 6ac25aae10 Fixes based on test run
Had issues with Array env variables in tmt
Propose some minor changes in e2e/lib/test

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-06-07 16:40:24 +03:00
Yariv Rachmani bcfeb8828b Rebase with latest changes
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-06-07 16:40:24 +03:00
Douglas Landgraf 32c88d0575
Merge pull request #81 from Yarboa/add-flake8
Adding flake8 to precommit
2023-06-06 13:06:46 -04:00
Yariv Rachmani 31c279b697 Fix flake8 shell check
Update extra files under demos die

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-06-06 15:31:24 +03:00
Yariv Rachmani e63a1ad603 Updating directories for search
Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-06-06 12:19:50 +03:00
Yariv Rachmani c68c4bab1c Adding flake8 to precommit
Adding demo path for checking

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-06-06 09:17:34 +03:00
Douglas Landgraf 4a022c7c09
Merge pull request #80 from Yarboa/adding-precommit
Adding pre-commit workflow
2023-06-06 01:08:32 -04:00
Yariv Rachmani a53813d7c3 Fixing README.md
Fixing linting due to precommit ablaysis

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-06-05 23:19:44 +03:00
Yariv Rachmani 4c6e2d3e9e Adding pre-commit workflow
Resolve #79
[Fix] added non relevant action e2e, removed

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-06-05 23:18:52 +03:00
Daniel J Walsh c5ff05fa5c
Merge pull request #69 from Yarboa/tmt-tests
Add Packit test tmt plans
2023-05-31 16:44:36 -04:00
Yariv Rachmani da12f5748b Latest changes based on review
Updates readme with the data related to packit, testingfarm and tmt

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-05-31 13:27:17 +03:00
Yariv Rachmani 1e75af08d6 Adding testingfarm runner
Adding e2e workflow with centosstream9
As based of comments add tmt as part of packit tests

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-05-31 13:25:29 +03:00
Yariv Rachmani b364ec9e2d TMT plan to be used by Packit
Fixes based on test run
Had issues with Array env variables in tmt
Propose some minor changes in e2e/lib/test

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-05-31 13:25:29 +03:00
Daniel J Walsh fd0e1c3ec5
Merge pull request #70 from dougsland/main
demo/e2e: add dashboard-tui
2023-05-30 07:52:49 -04:00
Daniel J Walsh b8e43e8d5f
Merge pull request #68 from Yarboa/updates-for-centos9
Updating images iptables-services
2023-05-26 10:46:15 -04:00
Douglas Schilling Landgraf b664416d28 demo/e2e: add dashboard-tui
Initial dashboard-tui tool, requires tests/e2e/run-test-e2e
to setup the environment. After that, just run the tool.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-05-24 14:23:14 -04:00
Yariv Rachmani fdb2d1ee5e Updating images iptables-services
e2e tests failed consistently on CentosStream9 with errors
Error: netavark: code: 3, msg: modprobe: FATAL: Module ip
ptables v1.8.8 (legacy): can't initialize iptables table

Updating Readme/requirements to consume latest:
podman
hirte

Signed-off-by: Yariv Rachmani <yrachman@redhat.com>
2023-05-22 21:28:13 +03:00
Lokesh Mandvekar 1592a66e2f
Merge pull request #67 from rhatdan/selinux
Additional SELinux rules found in testing
2023-05-21 14:31:00 -04:00
Daniel J Walsh 84886c0fbf
Additional SELinux rules found in testing
Bump to v0.4.2

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-21 07:38:40 -04:00
Lokesh Mandvekar 8690baa1d0
Merge pull request #66 from rhatdan/selinux
allow qm to set quota
2023-05-18 16:07:13 -04:00
Daniel J Walsh d9f511fb01
allow qm to set quota
Bump to v0.4.1

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-18 15:59:53 -04:00
Daniel J Walsh df1ac5a30c
Merge pull request #65 from lsm5/nproc-1
RPM: account for nproc == 1 and update correct quadlet file
2023-05-18 15:58:41 -04:00
Lokesh Mandvekar ef85266f0c
RPM: account for nproc == 1 and update correct quadlet file
Also set Epoch: 101 for builds in copr projects owned by rhcontainerbot.

Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-05-18 15:50:21 -04:00
Lokesh Mandvekar 0621d9f89b
Merge pull request #64 from rhatdan/main
Bump to v0.4.0
2023-05-18 10:34:37 -04:00
Daniel J Walsh c885ec5ac9
Bump to v0.4.0
We never really released v0.3.0, but a lot of good
features got added shortly after we started to release.

So I bumped the release again.

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-18 10:25:18 -04:00
Daniel J Walsh 882b67e470
Merge pull request #62 from lsm5/adjust-epel9
Packit: Temporarily disable bodhi for epel9
2023-05-18 10:22:58 -04:00
Lokesh Mandvekar 2a5d8fbbfe
Merge pull request #63 from rhatdan/quadlet
Switch all references to ROOTFS to capatalize
2023-05-18 10:03:29 -04:00
Lokesh Mandvekar 1cfd9786d4
Packit: Temporarily disable bodhi for epel9
Podman v4.5 and hirte-agent are not yet available on epel9 so
this commit removes those dependencies for epel9 and leaves it to the
user to fetch those.

Bodhi updates are also disabled so the built package never gets submitted to
any yum repo.

Refs:
1. https://bodhi.fedoraproject.org/updates/FEDORA-EPEL-2023-77d64cf134#comment-3026157
2. https://github.com/containers/qm/pull/59#issuecomment-1551691316

Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-05-18 10:03:06 -04:00
Daniel J Walsh 3f09c0de91
Switch all references to ROOTFS to capatalize
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-18 09:31:14 -04:00
Daniel J Walsh 1b7c966e92
Merge pull request #61 from rhatdan/quadlet
Fix handling of /var and /etc within container
2023-05-18 09:18:23 -04:00
Daniel J Walsh 44bccbc515
Fix handling of /var and /etc within container
With the current code using builtin volumes users on the
host system can not modify the ROOTFS/var and ROOTFS/etc
directories.
This PR just remounts these directories on top of themselves
read/write allowing users from the host to modify the
directories and the processes inside of the container to modify
them.
Both the host and the QM will be able to see the modifications.

Added a ROOTFS=/usr/lib/qm/rootfs environment variable to make
the quadlet easier to understand.

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-17 17:16:51 -04:00
Lokesh Mandvekar 115890a3df
Merge pull request #60 from rhatdan/agent
Bump to v0.3.0
2023-05-17 15:32:03 -04:00
Daniel J Walsh 778c36cd53
Bump to v0.3.0
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-17 15:06:51 -04:00
Daniel J Walsh 683e988643
Merge pull request #57 from rhatdan/agent
Update qm /etc/agent/agent.conf that when the qm.service is started
2023-05-17 15:05:18 -04:00
Daniel J Walsh a306ea1b70
Update qm /etc/agent/agent.conf that when the qm.service is started
This pull request will cause the /usr/lib/qm/rootfs/etc/hirte/agent.conf
to be created on every qm.service start.  This way if the admin changes
the /etc/hirte/agent.conf on the host, the equivalent inside of the qm
will match with the exception that the nodename is prefixed with qm.

If the nodename in the hosts /etc/hirte/agent.conf is changed to foobar,
then the qm's /etc/hirte/agent.conf will have the same settings except
the node name will be qm.foobar.

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-17 13:57:03 -04:00
Daniel J Walsh 753fb5c79a
Merge pull request #58 from dougsland/main123
e2e: add initial getopt
2023-05-17 11:36:04 -04:00
Lokesh Mandvekar 6df72e53bc
Merge pull request #56 from rhatdan/main
No longer need the --nogpgcheck flag
2023-05-17 09:13:32 -04:00
Daniel J Walsh 4d63514f3e
No longer need the --nogpgcheck flag
Seemed to be a temporary bug in fedora 38

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-17 08:57:45 -04:00
Lokesh Mandvekar 58deeada21
Merge pull request #55 from containers/pypingou-patch-2
Quick doc fix in the setup script
2023-05-17 08:49:03 -04:00
Lokesh Mandvekar efdb6f73c7
Merge pull request #53 from rhatdan/main
Changes needed for demoing on centos 9 stream
2023-05-17 08:48:25 -04:00
Pierre-Yves Chibon 52a41c822a
Quick doc fix in the setup script
The lines documenting what the script does (at the beginning
of the script) were pointing to the wrong path/folder being
created by this script.

This patch fixes that path to be the correct one

Signed-off-by: Pierre-Yves Chibon <pingou@pingoured.fr>
2023-05-17 13:45:52 +02:00
Daniel J Walsh a9263290d0
Changes needed for demoing on centos 9 stream
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-17 06:14:18 -04:00
Daniel J Walsh 34fd77860b
Merge pull request #52 from dougsland/coderevs
github: add dougsland as reviewer
2023-05-17 06:13:30 -04:00
Douglas Schilling Landgraf 9f53c45e39 e2e: add initial getopt
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-05-16 22:33:10 -04:00
Douglas Schilling Landgraf 7680b7a927 github: add dougsland as reviewer
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-05-16 18:42:10 -04:00
Lokesh Mandvekar cbe101fd84
Merge pull request #51 from lsm5/version-consistency
Packit: check for version consistency in VERSION and qm.te
2023-05-16 15:29:24 -04:00
Lokesh Mandvekar d2f45228b1
Packit: check for version consistency in VERSION and qm.te
The version is mentioned in two places in the repo. This commit will
check for version consistency before proceeding with packit tasks and
fail on mismatch.

Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-05-16 15:12:49 -04:00
Daniel J Walsh 6d5730c1ab
Merge pull request #50 from lsm5/bump-version
qm.te: Bump version
2023-05-16 13:49:42 -04:00
Lokesh Mandvekar 6bd0c2cddc
qm.te: Bump version
Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-05-16 13:41:50 -04:00
Daniel J Walsh f6b269f6ea
Merge pull request #49 from rhatdan/version
Bump to v0.2.0
2023-05-16 11:27:10 -04:00
Daniel J Walsh 481093ea84
Bump to v0.2.0
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-16 11:26:24 -04:00
Daniel J Walsh 07157cae73
Merge pull request #47 from rhatdan/demo
Build selinux on platforms without user_namespace class
2023-05-16 11:26:11 -04:00
Daniel J Walsh 013687d21d
Build selinux on platforms without user_namespace class
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-16 11:16:59 -04:00
Daniel J Walsh 529c1ee8f2
Merge pull request #48 from lsm5/podman-epoch
RPM: adjust podman dependency epoch
2023-05-16 10:39:57 -04:00
Lokesh Mandvekar 3072622f99
RPM: adjust podman dependency epoch
Ref: https://bodhi.fedoraproject.org/updates/FEDORA-EPEL-2023-9edad6c8f4

Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-05-16 10:16:05 -04:00
Daniel J Walsh 9bdb8f2eac
Merge pull request #46 from rhatdan/demo
Improve demo
2023-05-16 09:27:21 -04:00
Daniel J Walsh 4033ed1f47
Improve demo
Add demonstration of adding additional services

Add demonstrations of setting up a ASIL service that
can communicate with the qm environment.

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-15 11:28:01 -04:00
Daniel J Walsh 6976a8931f
Merge pull request #44 from rhatdan/selinux
update to allow unconfined_r to run qm_t
2023-05-15 09:58:00 -04:00
Daniel J Walsh 293d379701
Merge pull request #45 from rhatdan/demo
Add demo script to allow people to play with qm
2023-05-15 09:57:50 -04:00
Daniel J Walsh e5205fd179
Add demo script to allow people to play with qm
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-15 09:38:34 -04:00
Daniel J Walsh 4d488957e9
update to allow unconfined_r to run qm_t
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-15 09:36:51 -04:00
Daniel J Walsh 45e661b077
Merge pull request #42 from dougsland/codeowners
build: add .github/CODEOWNERS
2023-05-15 09:34:50 -04:00
Daniel J Walsh b74d1c707d
Merge pull request #43 from dougsland/fuse
qm.container: add /dev/fuse
2023-05-15 09:34:08 -04:00
Douglas Schilling Landgraf 715480aa21 qm.container: add /dev/fuse
fuse is required for nested container

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-05-14 08:16:28 -04:00
Douglas Schilling Landgraf 2bfa75f1e7 build: add .github/CODEOWNERS
Automatically add owners to review new PRs.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-05-14 08:12:54 -04:00
Daniel J Walsh ab79770072
Merge pull request #41 from dougsland/e2eaddvalidations
e2e: add validations for calls
2023-05-14 07:02:51 -04:00
Douglas Schilling Landgraf 1d39f9e8df e2e: add validations to lib/systemd
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-05-13 08:04:48 -04:00
Douglas Schilling Landgraf ebfcdd1c10 e2e: improve code readability.
add also a validation

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-05-13 08:04:22 -04:00
Douglas Schilling Landgraf 971d26e74b e2e: lib/container add validations
Added several validations and failures msgs.

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-05-13 08:03:30 -04:00
Douglas Schilling Landgraf 26fe1780de e2e: get_ip_container improvements
- simplify get_ip_container and handler exit from subshell
- cleanups and removed dead code
- use kill$$ from subshell
- add IP_CONTROL_MACHINE var
- return error if get_ip_container fails

Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-05-13 08:03:02 -04:00
Lokesh Mandvekar 76d86422bc
Merge pull request #34 from dougsland/e2e
e2e: Initial e2e code
2023-05-11 11:24:48 -04:00
Douglas Schilling Landgraf 5d81bf388e e2e: Initial e2e code
GH-Issue: https://github.com/containers/qm/issues/33
Signed-off-by: Douglas Schilling Landgraf <dougsland@redhat.com>
2023-05-11 11:17:06 -04:00
Daniel J Walsh a9d01a256f
Merge pull request #40 from rhatdan/selinux
Allow qm_t to be entered from all executables
2023-05-11 10:54:46 -04:00
Daniel J Walsh 1b7f437729
Allow qm_t to be entered from all executables
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-11 08:23:37 -04:00
Daniel J Walsh 477c19ec98
Merge pull request #39 from rhatdan/selinux
Add configuration of storage.conf for qm
2023-05-10 15:21:40 -04:00
Daniel J Walsh 1f7d506d9d
Add configuration of storage.conf for qm
We want to configure storage inside of the qm to use transient store.

Setup /var/lib/shared directory to be available to be volume mounted
from the host, if it is not volume mounted then we need to make sure
the storage still works.

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-10 13:20:43 -04:00
Daniel J Walsh 39f7f41d91
Merge pull request #38 from rhatdan/selinux
Additional SELinux fixes
2023-05-10 12:18:39 -04:00
Daniel J Walsh 2285615b8f
Extend support for additionalstores
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-10 11:00:54 -04:00
Daniel J Walsh 15c886a12c
Allow qm_t to mounton selinux file system
Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
2023-05-10 11:00:54 -04:00
Daniel J Walsh b4f182c4f4
Merge pull request #37 from lsm5/packit-fix-tarball-path
Packit: fix source tarball path
2023-05-10 10:41:12 -04:00
Lokesh Mandvekar 3bdf984295
Packit: fix source tarball path
Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-05-10 08:44:57 -04:00
Daniel J Walsh b9358b49c9
Merge pull request #36 from lsm5/packit-downstream
Packit: Add downstream Fedora packaging tasks
2023-05-09 17:19:58 -04:00
Lokesh Mandvekar 71b872a5a0
Packit: Add downstream Fedora packaging tasks
Get rid of `qm.spec.rpkg` in favour of
`rpm/qm.spec` which gets synced with fedora dist-git on every
upstream release. The version in the new spec file is set to `0` by
default and gets updated by packit automatically on every packit task.

For local manual rpm builds using the spec, the helper script in the
`rpm/` subdir will update the Version field with the latest version
found in the upstream repo.

Packit will automatically create a PR on fedora dist-git on every new
upstream release. A sample PR will look like:
https://src.fedoraproject.org/rpms/container-selinux/pull-request/10#

A dry run for this can be triggered using:
`$ packit propose-downstream --local-content`

To run this command locally, you would need to have your packit
user-configuration-file set.
Ref: https://packit.dev/docs/configuration/#user-configuration-file

along with a fedora api key created at:
https://src.fedoraproject.org/settings#nav-api-tab with sufficient ACLs.

Fedora 37 has been removed from packit targets because we are not
supporting qm there.

Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-05-09 12:19:13 -04:00
Daniel J Walsh 9db6965d1b
Merge pull request #31 from lsm5/allowed-cpus-sane-default
quadlet: minimal sane default for AllowedCPUs
2023-05-05 17:09:50 -04:00
Lokesh Mandvekar 3f81fa3f0f
quadlet: minimal sane default for AllowedCPUs
Set `AllowedCPUs=` to a minimal sane default which should work for most
if not all users.

RPM packaging can optimize this for the env in postinstall.

Signed-off-by: Lokesh Mandvekar <lsm5@fedoraproject.org>
2023-05-05 13:52:37 -04:00
Daniel J Walsh 4ce04a25bd
Merge pull request #30 from rhatdan/main
Init version 0.1.0
2023-05-05 09:29:33 -04:00
281 changed files with 16107 additions and 332 deletions

1
.fmf/version Normal file
View File

@ -0,0 +1 @@
1

5
.github/CODEOWNERS vendored Normal file
View File

@ -0,0 +1,5 @@
# See github docs for more info on the syntax:
# https://docs.github.com/en/repositories/managing-your-repositorys-settings-and-features/customizing-your-repository/about-code-owners
# Default to all maintainers if nothing more specific matches
* @rhatdan @dougsland @yarboa @nsednev @aesteve-rh @pengshanyu @kleinffm

18
.github/workflows/check-cgroup.yml vendored Normal file
View File

@ -0,0 +1,18 @@
name: Check Cgroup Version
on: [push, pull_request] # Trigger on push or pull request. Adjust as needed.
jobs:
check-cgroup:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v3
- name: Check cgroup version
run: |
echo "Checking cgroup version and settings..."
grep cgroup /proc/filesystems
mount | grep cgroup
cat /proc/cgroups
cat /sys/fs/cgroup/cgroup.controllers

41
.github/workflows/check-python-bandit vendored Executable file
View File

@ -0,0 +1,41 @@
#!/bin/bash
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
# Function to check if a file is a Python script
is_python_script() {
local file="$1"
# Check if the file extension is .py or .python
if [[ "$file" == *.py ]]; then
return 0 # It's a Python script
fi
# Check if the file starts with a Python shebang
if head -n 1 "$file" | grep -qE '^#!/usr/bin/env python(3)?|^#!/usr/bin/python(3)?'; then
return 0 # It's a Python script
else
return 1 # Not a Python script
fi
}
# Directory to search (default is current directory)
search_dir="${1:-.}"
# Find all files (excluding directories)
find "$search_dir" -type f | while read -r file; do
if is_python_script "$file"; then
echo "Python script found: $file"
# Execute Bandit on the found Python script
bandit -r "$file"
fi
done

42
.github/workflows/check-subpackages.yml vendored Normal file
View File

@ -0,0 +1,42 @@
name: Build Subpackages
on:
pull_request
jobs:
build-subpackages:
runs-on: ubuntu-latest
container:
image: fedora:latest # Use Fedora as the container image
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Install dependencies
run: sudo dnf install -y git make rpmdevtools rpmbuild
- name: Run make for each subsystem
run: |
subsystem_build_failures=()
for dir in subsystems/*; do
if [ -d "$dir" ]; then
subsystem=$(basename "$dir")
echo "Running make for $subsystem..."
make TARGETS=$subsystem subpackages
if [ $? -ne 0 ]; then
subsystem_build_failures+=("$subsystem")
echo "❌ Make failed for $subsystem" >&2
fi
fi
done
if (( ${#subsystem_build_failures[@]} == 0 )); then
echo "✅ All subsystems built successfully"; \
exit 0;
else
echo "❌ The following subsystems failed to build: ";
echo -e "\t${subsystem_build_failures[@]}" | tr ' ' ', ';
exit 1;
fi

38
.github/workflows/check-with-bandit.yml vendored Normal file
View File

@ -0,0 +1,38 @@
name: Python Security Check
on:
push:
branches:
- main
pull_request:
branches:
- main
jobs:
bandit-check:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v3
- name: Set up Python
uses: actions/setup-python@v4
with:
python-version: '3.x'
- name: Install Bandit
run: |
python -m pip install --upgrade pip
pip install bandit
- name: Run Python Security Check script
run: |
./.github/workflows/check-python-bandit .
- name: Upload Bandit report
if: always()
uses: actions/upload-artifact@v4
with:
name: bandit-report
path: bandit-output.txt

30
.github/workflows/mkdocs-check.yml vendored Normal file
View File

@ -0,0 +1,30 @@
name: MkDocs Build Check
on:
pull_request:
paths:
- 'docs/**'
- '**.md'
jobs:
mkdocs-build:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v3
- name: Set up Python
uses: actions/setup-python@v4
with:
python-version: '3.x'
- name: Install MkDocs and dependencies
run: |
pip install \
mkdocs \
mkdocs-material \
pymdown-extensions
- name: Build MkDocs site
run: mkdocs build -f docs/mkdocs.yml --strict

47
.github/workflows/oci-hooks-tests.yml vendored Normal file
View File

@ -0,0 +1,47 @@
name: OCI Hooks Tests
on:
push:
paths:
- 'oci-hooks/**'
pull_request:
paths:
- 'oci-hooks/**'
jobs:
test:
runs-on: ubuntu-latest
container: python:3.11-slim
steps:
- name: Checkout repository
uses: actions/checkout@v3
- name: Set up Go
uses: actions/setup-go@v4
with:
go-version: '1.21'
- name: Install dependencies
run: |
apt-get update && apt-get install -y jq
pip install tox
# Install shfmt for shell script formatting
go install mvdan.cc/sh/v3/cmd/shfmt@latest
- name: Make OCI hook scripts executable
run: |
chmod +x oci-hooks/qm-device-manager/oci-qm-device-manager
chmod +x oci-hooks/wayland-client-devices/oci-qm-wayland-client-devices
- name: Run code quality checks
run: |
cd oci-hooks
tox -e lint
- name: Run tests
env:
FORCE_MOCK_DEVICES: true
run: |
cd oci-hooks
tox -e all

21
.github/workflows/pre-commit.yml vendored Normal file
View File

@ -0,0 +1,21 @@
name: pre-commit-checks
on:
pull_request
jobs:
pre_commit:
name: Check code with precommit
runs-on: ubuntu-latest
steps:
- name: Install Python
uses: actions/setup-python@v5
with:
python-version: '3.10'
- name: Checkout code
uses: actions/checkout@v4
- name: Run precommit check
uses: pre-commit/action@v3.0.1

4
.gitignore vendored
View File

@ -1,5 +1,9 @@
/*.tar.gz
rpmbuild/
tmp
qm.pp.bz2
*~
qm_file_contexts
*.8
tests/e2e/ContainerFile.template
__pycache__/

View File

@ -6,22 +6,34 @@
set -eo pipefail
# Set path to rpm spec file
SPEC_FILE=rpm/qm.spec
# Get Version from HEAD
HEAD_VERSION=$(grep '^policy_module' qm.te | sed 's/[^0-9.]//g')
# Check version consistency in qm.te and VERSION before proceeding
if [[ $(cat VERSION) != "${HEAD_VERSION}" ]]; then
echo "Inconsistent versions mentioned in VERSION and qm.te files. Investigate!"
echo "Aborting Packit tasks!"
exit 1
fi
# Generate source tarball
git archive --prefix=qm-$HEAD_VERSION/ -o qm-$HEAD_VERSION.tar.gz HEAD
git archive --prefix="qm-${HEAD_VERSION}/" -o "rpm/qm-${HEAD_VERSION}.tar.gz" HEAD
# RPM Spec modifications
# Update Version in spec with Version from qm.te
sed -i "s/^Version:.*/Version: $HEAD_VERSION/" qm.spec
sed -i "s/^Version:.*/Version: ${HEAD_VERSION}/" ${SPEC_FILE}
# Update Release in spec with Packit's release envvar
sed -i "s/^Release:.*/Release: $PACKIT_RPMSPEC_RELEASE%{?dist}/" qm.spec
sed -i "s/^Release:.*/Release: ${PACKIT_RPMSPEC_RELEASE}%{?dist}/" ${SPEC_FILE}
# Update Source tarball name in spec
sed -i "s/^Source:.*.tar.gz/Source: %{name}-$HEAD_VERSION.tar.gz/" qm.spec
sed -i "s/^Source0:.*.tar.gz/Source0: %{name}-${HEAD_VERSION}.tar.gz/" ${SPEC_FILE}
# Add update create additional subpackages in spec
# Please refer `Let automation create/publish PR sub-packages` of docs/devel/README.md
sed -i 's/\(enable_qm_mount_bind_kvm \).*/\11/' ${SPEC_FILE}
# Update setup macro to use the correct build dir
sed -i "s/^%setup.*/%autosetup -Sgit -n %{name}-$HEAD_VERSION/" qm.spec

View File

@ -2,66 +2,157 @@
# See the documentation for more information:
# https://packit.dev/docs/configuration/
# Build targets can be found at:
# https://copr.fedorainfracloud.org/coprs/rhcontainerbot/packit-builds/
specfile_path: rpm/qm.spec
upstream_tag_template: v{version}
specfile_path: qm.spec
srpm_build_deps:
- make
actions:
fix-spec-file:
- bash .packit.sh
jobs:
- &copr
job: copr_build
# Run on every PR
- job: copr_build
trigger: pull_request
owner: rhcontainerbot
project: packit-builds
enable_net: true
# x86_64 is assumed by default
# qm is noarch so we only need to test on one arch
targets:
- fedora-rawhide
- fedora-38
- fedora-37
- centos-stream-9
srpm_build_deps:
- make
- rpkg
actions:
post-upstream-clone:
- rpkg spec --outdir ./
fix-spec-file:
- bash .packit.sh
fedora-development: {}
fedora-latest: {}
epel-9:
additional_repos:
- copr://@centos-automotive-sig/bluechi-snapshot
epel-10:
additional_repos:
- copr://@centos-automotive-sig/bluechi-snapshot
- <<: *copr
# Run on commit to main branch
# Run on commit to main branch
- &copr
job: copr_build
trigger: commit
branch: main
project: podman-next
targets:
- fedora-rawhide-aarch64
- fedora-rawhide-ppc64le
- fedora-rawhide-s390x
- fedora-rawhide-x86_64
- fedora-38-aarch64
- fedora-38-ppc64le
- fedora-38-s390x
- fedora-38-x86_64
- fedora-37-aarch64
- fedora-37-ppc64le
- fedora-37-s390x
- fedora-37-x86_64
- centos-stream+epel-next-9-aarch64
- centos-stream+epel-next-9-ppc64le
- centos-stream+epel-next-9-s390x
- centos-stream+epel-next-9-x86_64
owner: "@centos-automotive-sig"
project: qm-next
enable_net: true
notifications:
failure_comment:
message: "QM build failed for merged commit {commit_sha}. Please check logs {logs_url}"
- <<: *copr
# Run on commit to main branch
trigger: commit
branch: main
project: qm
targets:
- centos-stream-9-aarch64
- centos-stream-9-ppc64le
- centos-stream-9-s390x
- centos-stream-9-x86_64
- fedora-stable-aarch64
- fedora-stable-ppc64le
- fedora-stable-x86_64
- epel-9-aarch64
- epel-9-ppc64le
- epel-9-x86_64
- epel-10-aarch64
- epel-10-ppc64le
- epel-10-x86_64
- job: tests
trigger: pull_request
identifier: e2e-multi-bluechi-agents
tmt_plan: /plans/e2e/multi-bluechi-agents
targets:
- epel-9-x86_64
manual_trigger: true
tf_extra_params:
environments:
- artifacts:
- &bluechi_copr_repo
type: repository-file
id: https://copr.fedorainfracloud.org/coprs/g/centos-automotive-sig/bluechi-snapshot/repo/centos-stream-9
- &bluechi_copr_repo_fedora
type: repository-file
id: https://copr.fedorainfracloud.org/coprs/g/centos-automotive-sig/bluechi-snapshot/repo/fedora
hardware:
disk:
- size: ">= 20 GB"
- job: tests
trigger: pull_request
identifier: e2e-ffi
tmt_plan: /plans/e2e/ffi
targets:
- epel-9-x86_64
tf_extra_params:
environments:
- artifacts:
- *bluechi_copr_repo
tmt:
context:
scenario : "ffi"
hardware:
disk:
- size: ">= 20 GB"
- size: ">= 20 GB"
- job: tests
trigger: pull_request
identifier: qm-tier-0
tmt_plan: /plans/e2e/tier-0
targets:
- epel-9-x86_64
tf_extra_params:
environments:
- artifacts:
- *bluechi_copr_repo
hardware:
disk:
- size: ">= 20 GB"
- job: tests
trigger: pull_request
identifier: kvm-tier-0
tmt_plan: /plans/e2e/kvm-tier-0
targets:
# TBF: fedora-latest -eq 42 no published to public-tf
- fedora-41
- epel-9-x86_64
tf_extra_params:
environments:
- artifacts:
- *bluechi_copr_repo_fedora
hardware:
disk:
- size: ">= 20 GB"
virtualization:
is-supported: true
- job: tests
trigger: pull_request
identifier: automotive-image-builder
tmt_plan: /plans/e2e/aib
targets:
- epel-9-x86_64
tf_extra_params:
environments:
hardware:
disk:
- size: ">= 20 GB"
- job: propose_downstream
trigger: release
dist_git_branches:
- fedora-all
- epel-9
- epel-10
- job: koji_build
trigger: commit
dist_git_branches:
- fedora-all
- epel-9
- epel-10
- job: bodhi_update
trigger: commit
dist_git_branches:
# rawhide updates are created automatically
- fedora-branched
- epel-9
- epel-10

42
.pre-commit-config.yaml Normal file
View File

@ -0,0 +1,42 @@
# See https://pre-commit.com for more information
# See https://pre-commit.com/hooks.html for more hooks
repos:
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.6.0
hooks:
- id: trailing-whitespace
- repo: https://github.com/shellcheck-py/shellcheck-py
rev: v0.10.0.1
hooks:
- id: shellcheck
args: ["-x", "-a"]
- repo: https://github.com/igorshubovych/markdownlint-cli
rev: v0.41.0
hooks:
- id: markdownlint
args: ["--disable", "MD013", "MD041", "--"]
# MD041 disabled because pandoc requires first line to be a metadata block
# while markdownlint want it to be a level 1 header
- repo: https://github.com/PyCQA/flake8
rev: 7.1.0
hooks:
- id: flake8
args: ["-j8", "--ignore=B036,B902"]
additional_dependencies: [
'flake8-blind-except',
'flake8-docstrings',
'flake8-bugbear',
'flake8-comprehensions',
'flake8-docstrings',
'flake8-implicit-str-concat',
'pydocstyle>=5.0.0',
]
- repo: https://github.com/packit/pre-commit-hooks
rev: v1.2.0
hooks:
- id: validate-config

6
.pre-commit-hooks.yaml Normal file
View File

@ -0,0 +1,6 @@
- id: validate-config
name: Validate package config
description: Check for missing values and incorrect types
entry: ./pre-commit-hooks/validate-config.sh
language: script
files: ^\.?packit.ya?ml$

20
.readthedocs.yaml Normal file
View File

@ -0,0 +1,20 @@
# .readthedocs.yaml
# Read the Docs configuration file
# See https://docs.readthedocs.io/en/stable/config-file/v2.html for details
# Required
version: 2
# Set the version of Python and other tools you might need
build:
os: ubuntu-22.04
tools:
python: "3.11"
mkdocs:
configuration: docs/mkdocs.yml
# Optionally declare the Python requirements required to build your docs
python:
install:
- requirements: docs/requirements.txt

View File

@ -6,8 +6,20 @@ DATADIR ?= $(PREFIX)/share
LIBDIR ?= $(PREFIX)/lib
SYSCONFDIR?=/etc
QMDIR=/usr/lib/qm
SPECFILE=rpm/qm.spec
RPM_TOPDIR ?= $(PWD)/rpmbuild
VERSION ?= $(shell cat VERSION)
ROOTDIR ?= $(PWD)
file_contexts: qm.fc
# Default help target
.PHONY: help
help:
@echo "Available targets:"
@grep -E '^[a-zA-Z0-9_-]+:.*?## .*$$' $(MAKEFILE_LIST) | awk 'BEGIN {FS = ":.*?## "}; {printf "\033[36m%-20s\033[0m %s\n", $$1, $$2}'
@grep -E '^##@ .*$$' $(MAKEFILE_LIST) | sed 's/##@/\n\033[1;32m/' | sed 's/$$/\033[0m/'
.PHONY: file_contexts
file_contexts: qm.fc ## - Generates the qm_file_contexts
sed \
-e "s|${QMDIR}/rootfs||" \
-e "s/gen_context(//g" \
@ -16,29 +28,71 @@ file_contexts: qm.fc
all: selinux file_contexts man
selinux: qm.pp
.PHONY: selinux
selinux: qm.pp ## - Compresses the QM SELinux policy file (qm.pp)
@echo Compressing $^ -\> $@
bzip2 -f -9 $^
%.pp: %.te
make -f ${DATADIR}/selinux/devel/Makefile $@
mkdir -p tmp; cp qm.* tmp/
@if ./build-aux/validations ; then \
sed -i /user_namespace/d tmp/qm.if; \
fi
$(MAKE) -C tmp -f ${DATADIR}/selinux/devel/Makefile $@
cp tmp/qm.pp .; rm -rf tmp
.PHONY: codespell
codespell:
codespell: ## - Runs codespell to check for spelling errors
@codespell -S tmp,.git -L te -w
clean:
clean: ## - Removes generated files and dirs
rm -f *~ *.tc *.pp *.pp.bz2
rm -rf tmp *.tar.gz
rm -rf tmp *.tar.gz ${RPM_TOPDIR}
man: qm.8.md
man: qm.8.md ## - Generates the QM man page
go-md2man --in qm.8.md --out qm.8
install-policy: all
.PHONY: dist
dist: ## - Creates the QM distribution package
tar cvz \
--exclude='.git' \
--dereference \
--exclude='.gitignore' \
--exclude='.fmf' \
--exclude='.packit.*' \
--exclude='.pre-commit*' \
--exclude='.readthedocs.yaml' \
--exclude='demos' \
--exclude='docs' \
--exclude='plans' \
--exclude='subsystems' \
--exclude='tests' \
--exclude='.github' \
--transform s/qm/qm-${VERSION}/ \
-f /tmp/v${VERSION}.tar.gz ../qm
mv /tmp/v${VERSION}.tar.gz ./rpm
.PHONY: rpm
rpm: clean dist ## - Creates a local RPM package, useful for development
mkdir -p ${RPM_TOPDIR}/{RPMS,SRPMS,BUILD,SOURCES}
tools/version-update -v ${VERSION}
cp ./rpm/v${VERSION}.tar.gz ${RPM_TOPDIR}/SOURCES
rpmbuild -ba \
--define="_topdir ${RPM_TOPDIR}" \
--define="version ${VERSION}" \
${SPECFILE}
.PHONY: subpackages
subpackages: $(TARGETS)
$(TARGETS):
@echo "Entering directory: subsystem/$@"
make -f subsystems/$@/Makefile $@
install-policy: all ## - Install selinux policies only
semodule -i ${TARGETS}.pp.bz2
sepolicy manpage --path . --domain ${TARGETS}_t
install: man all
install: man all ## - Install QM files (including selinux)
install -D -pm 644 ${TARGETS}.pp.bz2 ${DESTDIR}${DATADIR}/selinux/packages/qm.pp.bz2
install -D -pm 644 qm.if ${DESTDIR}${DATADIR}/selinux/devel/include/services/qm.if
install -D -pm 644 qm_selinux.8 ${DESTDIR}${DATADIR}/man/man8/qm_selinux.8
@ -46,6 +100,13 @@ install: man all
install -d -m 755 ${DESTDIR}${DATADIR}/qm
install -D -m 644 qm_contexts ${DESTDIR}${DATADIR}/qm/contexts
install -D -m 755 setup ${DESTDIR}${DATADIR}/qm/setup
install -D -m 755 tools/comment-tz-local ${DESTDIR}${DATADIR}/qm/comment-tz-local
install -D -m 755 tools/qm-rootfs ${DESTDIR}${DATADIR}/qm/qm-rootfs
install -D -m 755 tools/qm-storage-settings ${DESTDIR}${DATADIR}/qm/qm-storage-settings
install -D -m 755 create-seccomp-rules ${DESTDIR}${DATADIR}/qm/create-seccomp-rules
install -D -m 644 qm_file_contexts ${DESTDIR}${DATADIR}/qm/file_contexts
install -D -m 644 containers.conf ${DESTDIR}${DATADIR}/qm/containers.conf
install -D -m 644 qm.container ${DESTDIR}${DATADIR}/containers/systemd/qm.container
install -D -m 755 tools/qm-is-ostree ${DESTDIR}${DATADIR}/qm/qm-is-ostree
install -D -m 755 tools/qmctl/qmctl ${DESTDIR}${PREFIX}/bin/qmctl
install -D -m 644 tools/qmctl/qmctl.1 ${DESTDIR}${DATADIR}/man/man1/qmctl.1

314
README.md
View File

@ -1,33 +1,303 @@
# QM is a containerized environment for running Functional Safety qm (Quality Management) software.
# Topics
The main purpose of this package is allow users to setup an environment which
prevents applications and container tools from interfering with other all
other processes on the system.
- [Topics](#topics)
- [QM is a containerized environment for running functional safety Quality Management software](#qm-is-a-containerized-environment-for-running-functional-safety-quality-management-software)
- [QM SELinux policy](#qm-selinux-policy)
- [BlueChi](#bluechi)
- [RPM building dependencies](#rpm-building-dependencies)
- [How OOM score adjustment is used in QM](#how-oom-score-adjustment-is-used-in-qm)
- [Priority process of OOM killer in the QM context](#priority-process-of-oom-killer-in-the-qm-context)
- [Contributing to the QM project](#contributing-to-the-qm-project)
- [Realtime](#realtime)
- [Talks and videos](#talks-and-videos)
- [RPM mirrors](#rpm-mirrors)
- [Configuring QM](#configuring-qm)
- [Modifying the `MemoryHigh` variable](#modifying-the-memoryhigh-variable)
The QM environment uses containerization tools like cgoups, namespaces, and
security isolation to prevent accidental interference by processes in the qm.
## QM is a containerized environment for running functional safety Quality Management software
The QM will run its own version of systemd and Podman to isolate not only the
applications and containers launched by systemd and Podman but systemd and
The main purpose of the Quality Management (QM) environment is to allow users to configure
an environment that prevents applications and container tools from interfering with
other processes on the system, such as in Automotive Safety Integrity Level (ASIL)
processes and applications. AutoSD is not a certified safety product. In the context of
AutoSD, QM is not for use in production environments but for research and learning purposes only.
The QM environment uses containerization tools, such as cgroups, namespaces, and
security isolation, to prevent accidental interference by processes in the QM.
The QM runs its own version of systemd and Podman to isolate not only the
applications and containers launched by systemd and Podman, but also systemd and
Podman commands themselves.
This package requires the Podman package to establish the containerized
environment and uses quadlet to set it up.
environment and uses Quadlet to set it up. Refer to the [docs directory](docs/quadlet-examples/)
for example Quadlet files.
Software install into the qm environment under /usr/lib/qm/rootfs will
be automatically isolated from the host. But if developers want to further
isolate these processes from other processes in the QM they can use container
tools like Podman to further isolate.
Software installed in the QM environment under `/usr/lib/qm/rootfs` is
automatically isolated from the host. To further isolate these processes
from other processes in the QM, developers can use container tools, such as Podman.
* SELinux Policy
## QM SELinux policy
This policy is used to isolate Quality Management parts of the operating system
from the other Domain-Specific Functional Safety Levels (ASIL).
The QM SELinux policy isolates QM parts of the operating system
from the other domain-specific functional safety levels, such as ASIL.
The main purpose of this policy is to prevent applications and container tools
with interfering with other processes on the system. The QM needs to support
further isolate containers run within the qm from the qm_t process and from
each other.
The main purpose of this policy is to prevent applications and container
tools from interfering with other processes on the system. The QM must
isolate containers from `qm_t` processes as well as from other containers.
For now all of the control processes in the qm other then containers will run
with the same qm_t type.
For now, all of the control processes in the QM other than containers run
with the same `qm_t` type. For more information, refer to `man qm_selinux`.
For support with a specific SELinux issue, open a [QM issue](https://github.com/containers/qm/issues)
and include the SELinux error output from a recent QM-related operation.
The following commands yield output that can help determine the root cause of the issue:
```console
ausearch -m avc -ts recent | audit2why
journalctl -t setroubleshoot
sealert -a /var/log/audit/audit.log
```
## BlueChi
- [BlueChi](https://github.com/containers/qm/pull/57)
The package configures the bluechi-agent within the QM.
BlueChi is a systemd service controller intended for use in highly regulated
ecosystems that feature multi-node environments with a predefined number of nodes.
Potential use cases can be found in industries that require functional safety,
such as the transportation industry in which services must be controlled across different
edge devices and where traditional orchestration tools do not comply with
regulatory requirements.
Systems with QM installed have two systemd processes running on them. The QM
bluechi-agent is based on the hosts `/etc/bluechi/agent.conf` file. By default, any
changes to the system's `agent.conf` file are reflected in the QM `/etc/bluechi/agent.conf` file.
You can further customize the QM bluechi-agent by adding content to the
`/usr/lib/qm/rootfs/etc/bluechi/agent.conf.d/` directory.
```console
# dnf install -y python3-dnf-plugins-core
# dnf config-manager --set-enabled crb
```
## RPM building dependencies
To build QM packages on CentOS Stream 9, enable the Code Ready Builder
repository for access to the `golang-github-cpuguy83-md2man` package.
## How OOM score adjustment is used in QM
The Linux host kernel controls ASIL and QM processes. The Out-of-Memory (OOM) Killer is part of the Linux
kernel's memory management subsystem. OOM Killer terminates processes to release RAM in memory-constrained conditions.
The `oom_score_adj` parameter refers to the Out-of-Memory score adjustment in Linux operating systems.
The OOM Killer uses the `oom_score_adj` parameter to decide which processes to terminate when the system is
critically low on memory.
By fine-tuning which processes are more likely to be terminated during low-memory situations,
critical processes can be protected, which enhances the overall stability of the system.
- For example, ASIL applications are essential to maintaining functional safety in automotive systems.
You can set their OOM score adjustment value from *-1* to *-1000*. To prioritize their operation
even in low-memory situations, setting the value to *-1000* makes the process immune to the OOM killer
and ensures that ASIL applications are the last to be terminated.
- The QM process has a default OOM score adjustment value set to *500*, configured via the `qm.container` file.
```console
cat /usr/share/containers/systemd/qm.container | grep OOMScoreAdjust
# OOMScoreAdjust=500
```
- All nested containers created inside the QM have a default OOM score adjustment of *750*.
```console
$ cat /usr/share/qm/containers.conf | grep oom_score_adj
oom_score_adj = 750
```
### Priority process of OOM killer in the QM context
```txt
+-------------------------------------------------------------+
| The Priority Process of OOM Killer in the QM Context |
+-------------------------------------------------------------+
------------------------------------ Kernel space -----------------------------------------------
+--------------------------------+
| Out of Memory Killer Mechanism |
| (OOM Killer) |
+--------------------------------+
|
v
+--------------------------------+
| Kernel Scheduler |
+--------------------------------+
------------------------------------ User space -------------------------------------------------
+----------------------------------------+
| Out of Memory Score Adjustment |
| (oom_score_adj) |
+----------------------------------------+
|
|
v (Processes Priority side by side)
+-----------------------------+--------------------------+-----------------------+
| | | |
v v v v
+------------------+ +----------------------------+ +-----------------+ +-----------------+
| | | | | | | |
| QM Container | | Nested Containers by QM | | ASIL Apps | | Other Processes |
| | | | | | | |
| OOM Score | | OOM Score | | OOM Score | | OOM Score |
| 500 | | 750 | | -1 to -1000 | | (default: 0) |
+------------------+ +----------------------------+ +-----------------+ +-----------------+
| | | |
v v v v
+----------------+ +----------------+ +--------------------+ +-----------------+
| Lower priority | | Higher priority| | Very low priority | | Default priority|
| for termination| | for termination| | for termination | | for termination |
+----------------+ +----------------+ +--------------------+ +-----------------+
|
|
|
v
+-------------------------------------------------------------+
| |
| In conclusion, all nested containers created inside QM have |
| their OOM score adjustment set to 750, making them more |
| likely to be terminated first compared to the QM process. |
| |
| When compared to ASIL applications, nested containers |
| will have an even higher likelihood of being terminated. |
| |
| Compared to other processes with the default adjustment |
| value of 0, nested containers are still more likely to be |
| terminated first, ensuring the system and ASIL apps are |
| kept as safe as possible. |
| |
+-------------------------------------------------------------+
------------------------------------ User space -------------------------------------------------
------------------------------------ Kernel space -----------------------------------------------
```
## Contributing to the QM project
For information about how to contribute to the QM project, see the [Developers documentation README](docs/devel/README.md).
## Realtime
To enable real-time removal of sched_* blockage via seccomp, use the following schema:
```bash
cat << EOF >> /etc/containers/systemd/qm.container.d/rt.conf
> [Container]
SeccompProfile=""
> EOF
```
## Talks and videos
Let's spread the knowledge regarding QM. If you have interesting content pertaining to
QM-related technology, please share it with us.
## RPM mirrors
Looking for a specific version of QM? Search the [CentOS Automotive SIG Stream Mirror](https://mirror.stream.centos.org/SIGs/9-stream/automotive/aarch64/packages-main/Packages/q/). The packages in CentOS Automotive SIG Stream Mirror are for experimentation only.
## Configuring QM
To run QM on an immutable OSTree-based OS, we use systemd units with Podman Quadlet.
For more information on how `podman-systemd.unit` works, refer to the manual:
`man podman-systemd.unit`
The default QM configuration drop-in file is located in `/usr/share/containers/systemd/qm.container`.
Modifying the original service file is not an option. Instead, create drop-in files to
modify the default configuration.
**NOTE:** The configuration is built in alphabetical order of the drop-in files.
### Modifying the `MemoryHigh` variable
To override the default settings, create a new drop-in `.conf` file in the
`/etc/containers/systemd/qm.container.d/` directory. This method ensures that QM memory
usage is controlled without modifying the base system configuration.
1. Check the current memory limit:
```bash
systemctl show -P MemoryHigh qm
infinity
```
The command output `infinity` indicates that `MemoryHigh` is unlimited. You can
see this setting in `/usr/share/containers/systemd/qm.container`.
1. Create a directory for the new drop-in file:
```bash
mkdir -p /etc/containers/systemd/qm.container.d/
```
1. Create a new drop-in file:
```bash
vim /etc/containers/systemd/qm.container.d/100-MemoryMax.conf
```
In this example, the new drop-in file is named `100-MemoryMax.conf`. You can choose a different name,
but be aware that the configuration is built in alphabetical order of the drop-in files.
1. Edit the file to add the following content:
```bash
[Service]
MemoryHigh=2G
```
`MemoryHigh` is specified in gigabytes. 2G means 2 gigabytes.
1. Preview the updated systemd configuration:
```bash
/usr/lib/systemd/system-generators/podman-system-generator {--user} --dryrun
```
1. Reload systemd and restart `qm.service` to apply the configuration changes:
```bash
systemctl daemon-reload
systemctl restart qm.service
```
1. Verify the value of `MemoryHigh`:
```bash
systemctl show -P MemoryHigh qm
2147483648
```
Memory values are displayed in bytes; 2147483648 bytes = 2G, which confirms that `MemoryHigh` is set to 2G.

View File

@ -1,4 +1,3 @@
## Security and Disclosure Information Policy for the qm Project
# Security and Disclosure Information Policy for the qm Project
The qm Project follows the [Security and Disclosure Information Policy](https://github.com/containers/common/blob/master/SECURITY.md) for the Containers Projects.

View File

@ -1 +1 @@
0.1.0
0.9

View File

@ -0,0 +1,32 @@
.git
.gitignore
demos
tests
rpmbuild
tools
subsystems
qm-windowmanager
.github
NOTICE
plans
create-seccomp-rules
qm_file_context
qm.te
build-aux
docs
qm_contexts
qm.if
qm_selinux.8
setup
rpm
qm.8.md
qm.fc
pre-commit-hooks
pre-commit-hooks/validate-config.sh
Makefile
.fmf/
.fmf/version
.packit.sh
.packit.yaml
.pre-commit-config.yaml
.pre-commit-hooks.yaml

14
build-aux/validations Executable file
View File

@ -0,0 +1,14 @@
#!/bin/bash
# shellcheck source=/dev/null
source /etc/os-release
versionid=$(echo "$VERSION_ID" | awk -F. '{print $1}')
id_os=$(echo "$ID" | grep -i -E "(centos|rhel|autosd)")
if [ "${versionid}" -le 9 ] && [ -n "${id_os}" ] ; then
# the sed command is required for the selinux
exit 0
fi
exit 1

View File

@ -1,8 +1,29 @@
[containers]
default_ulimits = []
default_sysctls = []
cgroup_conf=[
"memory.oom.group=1",
]
# Temporary default to host network until we fix private network bridge setup
# when the qm container doesn't unmask all the virtual filesystems.
netns="host"
# The om_score_adj refers to the "Out of Memory score adjustment" in Linux
# operating systems. This parameter is used by the Out of Memory (OOM)
# killer to decide which processes to terminate when the system is
# critically low on memory.
#
# All nested containers created with QM will be set to 750 as score.
# The QM process has default value as 500 set via qm.container file.
#
# $ cat qm.container | grep OOMScoreAdjust
# OOMScoreAdjust=500
#
oom_score_adj = 750
[network]
# The default is 10.88.0.0, but we need qm containers to have a
# different ip address range or routing becomes confused
default_subnet="10.89.0.0/16"

127
create-seccomp-rules Executable file
View File

@ -0,0 +1,127 @@
#!/bin/bash
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software Foundation,
# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
SECCOMP_CONTAINERS_FILE="/usr/share/containers/seccomp.json"
SYSCALLS_TO_DENY=("sched_setscheduler" "sched_setattr")
QM_PATH_SECCOMP="/usr/share/qm/seccomp-no-rt.json"
QM_DIR="${QM_PATH_SECCOMP%/*}"
function remove_seccomp_entry_from_allow() {
local syscall_name=$1
local seccomp_file_path=$2
temp_file=$(mktemp)
jq --tab \
--arg syscall "$syscall_name" \
'(.syscalls[] | select(.names[] == $syscall and .action == "SCMP_ACT_ALLOW").names) |= map(select(. != $syscall))' \
"${seccomp_file_path}" > "$temp_file" && mv "$temp_file" "${seccomp_file_path}"
rm "$temp_file" &> /dev/null
}
function add_syscall_deny_list() {
local syscall_name="$1"
local seccomp_file_path="$2"
local temp_file
temp_file=$(mktemp)
if [[ "$syscall_name" == "sched_setscheduler" ]]; then
jq --tab \
'.syscalls += [
{
"names": ["sched_setscheduler"],
"action": "SCMP_ACT_ALLOW",
"args": [
{
"index": 1,
"value": 0,
"valueTwo": 0,
"op": "SCMP_CMP_EQ"
}
],
"comment": "",
"includes": {},
"excludes": {}
},
{
"names": ["sched_setscheduler"],
"action": "SCMP_ACT_ALLOW",
"args": [
{
"index": 1,
"value": 3,
"valueTwo": 0,
"op": "SCMP_CMP_EQ"
}
],
"comment": "",
"includes": {},
"excludes": {}
},
{
"names": ["sched_setscheduler"],
"action": "SCMP_ACT_ALLOW",
"args": [
{
"index": 1,
"value": 5,
"valueTwo": 0,
"op": "SCMP_CMP_EQ"
}
],
"comment": "",
"includes": {},
"excludes": {}
}
]' "$seccomp_file_path" > "$temp_file" && mv "$temp_file" "$seccomp_file_path"
else
jq --tab \
--arg syscall "$syscall_name" \
'.syscalls += [{
"names": [$syscall],
"action": "SCMP_ACT_ERRNO",
"args": [],
"errnoRet": 1,
"errno": "EPERM"
}]' "$seccomp_file_path" > "$temp_file" && mv "$temp_file" "$seccomp_file_path"
fi
rm "$temp_file" &> /dev/null
}
# Main
if [ ! -f "${SECCOMP_CONTAINERS_FILE}" ]; then
echo "Exiting... unable to find ${SECCOMP_CONTAINERS_FILE}"
exit 1
fi
if [ ! -d "${QM_DIR}" ]; then
echo "Exiting... unable to find ${QM_DIR}"
exit 1
fi
# Copying original seccomp.json
cp "${SECCOMP_CONTAINERS_FILE}" "${QM_PATH_SECCOMP}"
for syscall in "${SYSCALLS_TO_DENY[@]}"; do
# Remove syscall entry from the allow list
remove_seccomp_entry_from_allow "${syscall}" "${QM_PATH_SECCOMP}"
# Add syscall to the deny list
add_syscall_deny_list "${syscall}" "${QM_PATH_SECCOMP}"
done

48
demos/asilservice Executable file
View File

@ -0,0 +1,48 @@
#!/bin/python
"""
Enable se_linux permission to socket.
Script enable se_linux fscreate and socketcreate
"""
import selinux
import socket
import os
import os.path
import shutil
import sys
socket_dir = "/run/asilservice"
socket_path = socket_dir + "/asilservice.sock"
if os.path.exists(socket_dir):
shutil.rmtree(socket_dir)
try:
selinux.setfscreatecon("system_u:object_r:qm_file_t:s0")
selinux.setsockcreatecon("system_u:system_r:qm_t:s0")
except BaseException as see:
# selinux is disabled
print("\nSELinux is disabled, such environment is not recommended\n")
print("\nSELinux Exception occured:", see)
pass
server = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
os.mkdir(socket_dir)
server.bind(socket_path)
server.listen(1)
conn, addr = server.accept()
try:
while True:
data = conn.recv(1024)
conn.send("ASIL reply: ".encode())
conn.send(data)
if data.decode().strip() == "goodbye" or \
data.decode().strip() == "quit":
break
except Exception as error:
print("Exception occured:", error)
print(sys.argv[0] + ": exited\n")
conn.close()

1
demos/dashboard-tui Symbolic link
View File

@ -0,0 +1 @@
../tests/e2e/dashboard-tui/

227
demos/demo Executable file
View File

@ -0,0 +1,227 @@
#!/usr/bin/env bash
# shellcheck disable=SC2120,SC1091,SC2181
# Setting up some colors for helping read the demo output.
# Comment out any of the below to turn off that color.
bold=$(tput bold)
cyan=$(tput setaf 6)
reset=$(tput sgr0)
export qm_quadlet=/etc/containers/systemd/qm.container
export rootfs=/usr/lib/qm/rootfs
read_color() {
echo -e "\n\n[Press enter to continue]"
read -r -p "${bold}$1${reset}"
}
exec_color() {
echo -e "\nCommand to be executed:"
echo -e "
\t${bold}$ $1${reset}\n"
read -rp "[Press enter to continue]"
eval "${1}"
if [ "$?" -ne 0 ]; then
echo "command has failed ${1}"
exit 1
fi
}
echo_color() {
echo "${cyan}$1${reset}"
}
check_command() {
required_cmds=(sudo podman dnf)
for required_cmd in "${required_cmds[@]}"; do
if ! command -v "${required_cmd}" &> /dev/null
then
echo "${1} command could not be found. Install ${1} to continue."
exit 1
fi
done
}
init() {
clear
check_command
if [ ! -f "./asilservice" ]; then
echo "The asilservice script not found, please check."
exit 1
fi
echo_color "Starting demo..."
echo -e " - Removing any previous configuration for qm...\n"
rpm -e qm &> /dev/null
sudo systemctl stop qm &> /dev/null
sudo podman rm qm --force -t 0 > /dev/null
sudo podman volume rm --force qmEtc qmVar > /dev/null
sudo podman --root /var/lib/shared rmi -i ubi9 > /dev/null
sudo rm -rf /usr/lib/qm > /dev/null
test -s ${qm_quadlet}.orig && sudo mv ${qm_quadlet}.orig ${qm_quadlet}
}
install() {
clear
bluechi_snapshot='dnf copr enable @centos-automotive-sig/bluechi-snapshot -y &> /dev/null'
eval "${bluechi_snapshot}"
if [ "$?" -ne 0 ]; then
echo "fail to enable copr."
fi
cmd_install='sudo dnf -y install qm \
bluechi bluechi-agent bluechi-ctl \
podman container-selinux; \
sudo dnf -y update qm bluechi bluechi-agent \
bluechi-ctl podman container-selinux'
echo_color "Installing packages"
eval "${cmd_install}"
if [ "$?" -ne 0 ]; then
echo "fail to install packages."
fi
clear
}
setup() {
echo_color "Executing setup"
echo_color "Staring and enabling bluechi on the host system"
echo_color "============================================="
exec_color "sudo systemctl start bluechi bluechi-agent"
echo
echo_color "Install and setup: /usr/lib/qm/rootfs"
echo_color "============================================="
exec_color "sudo /usr/share/qm/setup"
read -rp "[Press enter to continue]"
clear
}
status() {
exec_color "sudo systemctl status qm.service"
clear
}
cpuweight() {
exec_color "sudo systemctl set-property --runtime qm.service CPUWeight=50"
echo "Value stored in qm.service/cpu.weight:"
sudo cat /sys/fs/cgroup/qm.service/cpu.weight
exec_color "sudo systemctl set-property --runtime qm.service CPUWeight=10"
echo "Value stored in qm.service/cpu.weight:"
sudo cat /sys/fs/cgroup/qm.service/cpu.weight
echo -e "\n\n[Press enter to continue]"
read -r
}
podman_ctr() {
clear
exec_color "sudo podman exec -ti qm ps -eZ"
exec_color "sudo podman exec qm podman run alpine echo hi"
exec_color "sudo podman run ubi9 echo hi"
exec_color "sudo podman exec qm podman images"
exec_color "sudo podman images"
exec_color "sudo podman exec qm podman run --userns=auto alpine cat /proc/self/uid_map"
exec_color "sudo podman exec qm podman run --userns=auto alpine cat /proc/self/uid_map"
exec_color "sudo podman exec qm podman run --userns=auto alpine cat /proc/self/uid_map"
exec_color "sudo podman run --userns=auto ubi9 cat /proc/self/uid_map"
exec_color "sudo podman run --userns=auto ubi9 cat /proc/self/uid_map"
}
bluechi() {
clear
exec_color "sudo podman exec -ti qm podman pull registry.access.redhat.com/ubi8/httpd-24:latest"
exec_color "echo \"[Container]
Image=registry.access.redhat.com/ubi8/httpd-24
Network=host
\" > /tmp/myquadlet.container"
exec_color "sudo podman cp /tmp/myquadlet.container qm:/etc/containers/systemd/"
exec_color "sudo podman exec qm systemctl daemon-reload"
# read the actual configuration.. and add the new qm.control
source /etc/bluechi/bluechi.conf
# Append to the current configuration the new node and restart the service
sudo sed -i '/^AllowedNodeNames=/ s/$/,qm.control/' /etc/bluechi/bluechi.conf
exec_color "sudo systemctl restart bluechi"
# get the ip of controller via interface eth0
ip_controller=$(ip addr list eth0 |grep "inet " |cut -d' ' -f6|cut -d/ -f1)
eval "$(podman exec qm \
sed -i 's/^#ControllerHost=/ControllerHost='"${ip_controller}"'/g' \
/etc/bluechi/agent.conf
)"
eval "$(podman exec qm \
systemctl restart bluechi-agent
)"
exec_color "sudo bluechictl restart qm.control myquadlet.service"
exec_color "sudo bluechictl list-units | grep --color myquadlet"
# give time to server spin up
sleep 3
exec_color "curl 127.0.0.1:8080"
exec_color "sudo bluechictl stop qm.control myquadlet.service"
# requires true as return -1 (to show that myquadlet is gonet)
exec_color "sudo bluechictl list-units | grep --color myquadlet || true"
}
additional_store() {
test -s ${qm_quadlet}.orig || sudo cp ${qm_quadlet} ${qm_quadlet}.orig
exec_color "sudo podman --root /var/lib/shared pull ubi9"
exec_color "sudo podman --root /var/lib/shared images | grep -A 10 -B 10 --color ubi9"
# requires true as return -1 (to show the image doesn't exist)
exec_color "sudo podman exec qm podman images | grep -A 10 -B 10 --color ubi9 || true"
exec_color "sudo sed -i -e '\$aVolume=/var/lib/shared:/var/lib/shared:ro' /etc/containers/systemd/qm.container"
exec_color "sudo systemctl daemon-reload"
exec_color "sudo systemctl restart qm.service"
exec_color "sudo podman exec qm podman images | grep -A 10 -B 10 --color ubi9"
}
asilservice() {
# requires true as return -1 (to show that the asilservice is not available)
exec_color "grep -A 20 -B 20 --color system_u.*s0 asilservice || true"
exec_color "sudo mkdir -p /run/asilservice"
exec_color "sudo python ./asilservice &"
exec_color "sudo systemctl stop qm"
sudo -u root "podman volume rm --force qmEtc qmVar > /dev/null"
exec_color "sudo dnf -y install --installroot ${rootfs} nmap-ncat --nogpgcheck"
exec_color "sudo restorecon -R ${rootfs}"
exec_color "sudo sed -i -e '\$aVolume=/run/asilservice:/run/asilservice' /etc/containers/systemd/qm.container"
exec_color "sudo systemctl daemon-reload"
exec_color "sudo systemctl restart qm"
echo_color "Starting asilservice, type any command to get a reply from ASIL service or quit to exit."
# requires true as return -1 as users type quit or goodbye
exec_color "sudo podman exec -ti qm /usr/bin/nc -U /run/asilservice/asilservice.sock || true"
}
init
install
setup
status
cpuweight
podman_ctr
bluechi
additional_store
asilservice
echo "Demo is done"

View File

@ -0,0 +1,77 @@
# DevConf2024
- [Introduction](## Introduction)
- [Requirements](## Requirements)
- [Install](## Running the demo)
## Introduction
This demo runs uninterfered service containers, process, under the following:
- HOST partition
- QM partition
It demonstartes:
- How to use quadlet service files under HOST and QM partitions
- How to control services with bluechictl
Running the demo recommend environment for tests is inside CentOS-Stream-9
## Requirements
It is recommend to use vm environment for tests in CentOS-Stream-9 virtual machine
Follow the following procedure to prepare virtual machine
[Download and run vm](../../tests/e2e/README.md#run-tmt-tests-framework-locally)
ssh to vm
``` bash
ssh -oStrictHostKeyChecking=no -oUserKnownHostsFile=/dev/null "root@localhost" -p <port>
```
## Install and set QM partition
Once inside VM, install rpms
``` bash
dnf install git python3-pip podman
```
Under root directory run the following git commands
``` bash
git clone --depth=1 https://github.com/containers/qm.git
cd qm
git checkout -b devconf-update
git pull origin devconf-update
git sparse-checkout set --no-cone demos/devconf-2024
git sparse-checkout add tests/e2e
```
Run setup script, it installs & prepares QM partition filesystem
``` bash
cd demos/devconf-2024
bash -x setup
```
Check QM partition is running and active
``` bash
systemctl is-active qm
active
```
## Prepare demo services
The demo create containers under HOST partition and QM partition
``` bash
bash -x prepare-demo.sh
```
## Running the demo
Please refer the following demo (ADD LINK)

1
demos/devconf-2024/lib Symbolic link
View File

@ -0,0 +1 @@
../../tests/e2e/lib/

View File

@ -0,0 +1,82 @@
#!/bin/bash
#
# Copyright 2023 The qm Authors
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; If not, see <http://www.gnu.org/licenses/>.
# Capture the start time
START_TIME=$(date +%s)
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
# Add menu
# shellcheck source=/dev/null
source "${SCRIPT_DIR}"/lib/systemd
# shellcheck source=/dev/null
source "${SCRIPT_DIR}"/lib/utils
# Cleanup
cleanup_node_services
# Create host services
echo
info_message "Preparing HOST services"
info_message "=============================="
srvs_host=("safety" "cruise_control" "tires" "breaks")
create_stub_systemd_srv "" "" "${srvs_host[@]}"
# Run verification for HOST
for service in "${srvs_host[@]}"; do
bluechictl list-units localrootfs --filter \
"*${service}*" | grep active
if_error_exit "HOST ${service} service is not in running state"
done
info_message "${GRN}HOST services are running ${CLR}"
# Create QM services
echo
info_message "Preparing QM services"
info_message "=============================="
srvs_qm=("radio" "store" "stream_audio" "maps")
echo
create_stub_systemd_srv "" "qm" "${srvs_qm[@]}"
# Run verification for QM
for service in "${srvs_qm[@]}"; do
bluechictl list-units qm.localrootfs --filter \
"*${service}*" | grep active
if_error_exit "QM ${service} service is not in running state"
done
info_message "${GRN}QM services are running ${CLR}"
# Capture the end time
END_TIME=$(date +%s)
# Calculate the duration in seconds
DURATION=$((END_TIME - START_TIME))
# Calculate minutes and seconds
DAYS=$((DURATION / 86400))
HOURS=$(( (DURATION % 86400) / 3600 ))
MINUTES=$(( (DURATION % 3600) / 60 ))
SECONDS=$((DURATION % 60))
echo
info_message "${GRN}Running time for this script${CLR}"
info_message "\t- ${DAYS} days, ${HOURS} hours, ${MINUTES} minutes and ${SECONDS} seconds"

1
demos/devconf-2024/setup Symbolic link
View File

@ -0,0 +1 @@
../../tests/e2e/set-ffi-env-e2e

1
demos/devconf-2024/tools Symbolic link
View File

@ -0,0 +1 @@
../../tests/e2e/tools/

View File

@ -0,0 +1,109 @@
# Developers documentation
## Building QM rpm manually with changes
Building QM locally with changes for tests is a recommended practice,
especially for testing new features before submitting a pull request.
**1.** Prerequisite
```bash
dnf install -y rpm-build golang-github-cpuguy83-md2man selinux-policy-devel
```
**2.** Clone the repo
```bash
git clone https://github.com/containers/qm.git && cd qm
```
**3.** Build the RPM
Select a QM version that is a higher number from the current one.
For example, if today's QM version is 0.6.2, set it to 1.0 so that
the RPM created is identifiable as yours.
```bash
make clean && VERSION=1.0 make rpm
```
The rpm is created at the `${RPM_TOPDIR}/RPMS` folder, by default
`${PWD}/rpmbuild/RPMS`.
You can export **RPM_TOPDIR** to change the path where the rpm will be placed.
For example:
```bash
VERSION=1.0 RPM_TOPDIR=/USER/rpmbuild make rpm
```
## Building CentOS AutoSD and QM manually
During development, it is common to conduct integration tests to ensure your
changes work well with other components within the overall solution.
In our case, it's best to test against the CentOS Automotive Stream
Distribution (AutoSD) image.
Once you have the new [RPM](#building-qm-rpm-manually-with-changes), follow these steps:
**1.** Make sure the new rpm is located in **/USER/rpmbuild/RPMS/**
Example
```bash
ls /root/rpmbuild/RPMS/noarch/qm-1.0-1.noarch.rpm
/root/rpmbuild/RPMS/noarch/qm-1.0-1.noarch.rpm
```
**2.** Download additional packages required by the image
```bash
sudo dnf download --destdir /root/rpmbuild/RPMS/noarch/ selinux-policy selinux-policy-any
```
**3.** Create a local repository with the new package
```bash
dnf install createrepo_c -y
cd /root/rpmbuild/RPMS/noarch/
createrepo .
```
**4.** Clone the CentOS Automotive distro for the build
Ensure you meet the requirements for the CentOS Automotive Stream by
referring to [this link](https://sigs.centos.org/automotive/building/).
The following commands will execute:
- Install the podman package
- Clone the sample-images repository and required submodules (automotive-image-builder)
- Cleanups before a fresh build
- Finally creates a new qcow2 image (BASED ON distro name, mode (ostree or regular) and uses the qemu-qm-container sample image)
NOTE:
- The path for the new QM rpm file (/root/rpmbuild/RPMS/noarch)
- extra_rpms - useful for debug.
- ssh enabled
The command below utilises automotive-image-builder to produce a `qm-minimal` qcow2 image for cs9,
other example images such as `simple-qm-container` and the `simple-qm`
image can be found in the images directory of the sample-images repository.
```bash
dnf install podman -y && dnf clean all
git clone https://gitlab.com/CentOS/automotive/sample-images.git
git submodule update --init
cd sample-images/
rm -rf _build #Optional, only relevant after initial build
rm -rf *.qcow2 #Optional, only relevant after initial build
./automotive-image-builder/automotive-image-builder build --distro cs9 --mode package --define 'ssh_permit_root_login=true' --define 'ssh_permit_password_auth=true' --define 'extra_repos=[{"id":"local","baseurl":"file:///root/rpmbuild/RPMS/noarch"}]' --define 'extra_rpms=["qm-1.0", "vim-enhanced", "openssh-server", "openssh-clients", "python3", "polkit", "rsync", "strace", "dnf", "gdb"]' --target qemu --export qcow2 images/qm-minimal.mpp.yml cs9-qemu-qm-container.x86_64.qcow2
```
If you would like more information on building automotive images with automotive-image-builder, please see the
[Automotive SIG pages for AutoSD](https://sigs.centos.org/automotive/getting-started/about-automotive-image-builder/)
Run the virtual machine, default user: root, pass: password.
To change default values, use the [defaults.ipp.yml](https://gitlab.com/CentOS/automotive/src/automotive-image-builder/-/blob/main/include/defaults.ipp.yml) file.
```bash
./automotive-image-builder/automotive-image-runner --nographics ./cs9-qemu-qm-container.x86_64.qcow2
```

View File

@ -0,0 +1,21 @@
# Maintainer documentation
## Creating a new release
Initially, make sure to [bump **qm.te** and **VERSION** files in the git repo](https://github.com/containers/qm/pull/760) to the next release, i.e: *v0.7.5*.
After that, follow the steps below using GitHub UI.
**Create a new Release**
![Click on Releases](./pics/creatingreleases/00-Click-on-Releases.jpeg)
**Draft a new release**
![Draft a new release](./pics/creatingreleases/01-Draft-a-new-release.png)
**Create a new tag**
![Create a tag](./pics/creatingreleases/02-Create-a-tag.jpeg)
**Generate release notes**
![Generate release notes](./pics/creatingreleases/03-Generate-release-notes.jpeg)
**Publish Release**
![Click on publish release](./pics/creatingreleases/04-click-on-publish-release.jpeg)

Binary file not shown.

After

Width:  |  Height:  |  Size: 513 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 943 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 374 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 405 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 500 KiB

View File

@ -0,0 +1,536 @@
# Subpackages
Subpackages are **experimental approach** to deliver in a single point (RPM) dropin files
and additional requirements.
The qm project is designed to provide a flexible and modular environment for managing
Quality Management (QM) software in containerized environments. One of the key features
of the qm package is its support for sub-package(s), such as the qm-dropin sub-packages.
These sub-packages are not enabled by default and are optional. However, allow users
to easily extend or customize their QM environment by adding specific configurations,
tools, or scripts to the containerized QM ecosystem by simple installing or uninstalling
a RPM package into the system.
The key features of QM Sub-Packages are
- **Modularity**
- No configuration change, no typo or distribution rebuild/update.
- Just dnf install/remove from the traditional rpm schema.
- **Customizability**
- Users can easily add specific configurations to enhance or modify the behavior of their QM containers.
- **Maintainability**
- Sub-packages ensure that the base qm package remains untouched, allowing easy updates without breaking custom configurations.
- **Simplicity**
- Like qm-dropin provide a clear directory structure and templates to guide users in customizing their QM environment.
!!! note
The following sections describe the currently available QM subpackages.
## Building QM sub-packages
Choose one of the following sub-packages and build using make.
```bash
git clone git@github.com:containers/qm.git && cd qm
Example of subpackages: kvm, qm-oci-hooks, ros2, text2speech, windowmanager
make TARGETS=input subpackages
ls rpmbuild/RPMS/noarch/
qm-0.6.7-1.fc40.noarch.rpm qm_mount_bind_input-0.6.7-1.fc40.noarch.rpm
```
## Installing QM sub-packages
```bash
$ sudo dnf install ./rpmbuild/RPMS/noarch/qm_mount_bind_input-0.6.7-1.fc40.noarch.rpm
<SNIP>
Complete!
```
If QM is already running, restart or reload your QM container environment to apply the new configurations.
```bash
sudo systemctl daemon-reload
sudo podman restart qm
```
## Removing QM sub-packages
```bash
sudo rpm -e qm_mount_bind_input
```
## Creating your own drop-in QM sub-package
We recommend using the existing drop-in files as a guide and adapting them to your specific needs. However, here are the step-by-step instructions:
1) Add a drop-in file to: `etc/containers/systemd/qm.container.d/qm_dropin_<subpackage>.conf>`
2) Add your package as a sub-package to: `rpm/<subpackage_directory>/<subpackage>.spec`
3) Add the makefile for the sub-package and any files required by the sub-package to: `subsystems/<subpackage_directory>`
4) Test the sub-package build by running: `make clean && make TARGETS=<subpackage> subpackages`
5) Install your sub-package using: `dnf install -y rpmbuild/RPMS/noarch/<subpackage>*.noarch.rpm`
6) Restart podman container using: `sudo podman restart qm`
7) Additionally, test it with and without enabling the sub-package using (by default it should be disabled but there are cases where it will be enabled by default if QM community decide):
Example changing the spec and triggering the build via make (feel free to automate via sed, awk etc):
```bash
# Use make file to run specific subpackage
make TARGETS=windowmanager subpackages
```
## QM sub-package Video
The video sub-package exposes `/dev/video0` (or many video devices required) to the container. This feature is useful for demonstrating how to share a camera from the host system into a container using Podman drop-in. To showcase this functionality, we provide the following demo:
### Building the video sub-package, installing, and restarting QM
```bash
make TARGETS=video subpackages
sudo dnf install ./rpmbuild/RPMS/noarch/qm-mount-bind-video-0.6.7-1.fc40.noarch.rpm
sudo systemctl daemon-reload
sudo podman restart qm
```
This simulates a rear camera when the user shifts into reverse gear.
In this simulation, we created a systemd service that, every time it is started, captures a snapshot from the webcam, simulating the action of a rear camera. (Feel free to start and restart the service multiple times!)
```bash
host> sudo podman exec -it qm bash
bash-5.2# systemctl daemon-reload
bash-5.2# systemctl start rear-camera
# ls -la /var/tmp/screenshot.jpg
-rw-r--r--. 1 root root 516687 Oct 13 04:05 /var/tmp/screenshot.jpg
bash-5.2#
```
### Copy the screenshot to the host and view it
```bash
host> sudo podman cp qm:/var/tmp/screenshot.jpg .
```
Great job! Now imagine all the possibilities this opens up!
## QM sub-package Sound
### Step 1: Install the QM Mount Bind Sound Package
To set up sound cards in a QM environment using Podman, follow the steps below:
Run the following commands to install the `qm_mount_bind_sound` package and restart QM (if previously in use):
```bash
# Build and install the RPM for QM sound
git clone https://github.com/containers/qm.git && cd qm
make TARGETS=sound subpackages
sudo dnf install -y rpmbuild/RPMS/noarch/qm_mount_bind_sound-0.6.7-1.fc40.noarch.rpm
# Restart QM container (if already running)
sudo systemctl daemon-reload
sudo podman restart qm
```
### Step 2: Identify Sound Cards
After installing the drop-in and restarting QM, you need to identify which sound card in the Linux system will be used in QM. If you're familiar with your sound card setup feel free to skip this step.
To list the sound cards available on your system (in our case, we will pick the number 1):
```bash
cat /proc/asound/cards
```
**Example Output**:
```bash
0 [NVidia ]: HDA-Intel - HDA NVidia
HDA NVidia at 0x9e000000 irq 17
1 [sofhdadsp ]: sof-hda-dsp - sof-hda-dsp
LENOVO-20Y5000QUS-ThinkPadX1ExtremeGen4i
2 [USB ]: USB-Audio - USB Audio Device
Generic USB Audio at usb-0000:00:14.0-5, full speed
```
### Detecting Channels and Sample Rates
To list the supported number of channels and samples use `pactl` command:
```bash
pactl list sinks | grep -i 48000 | uniq
Sample Specification: s24-32le 2ch 48000Hz
```
### Verify Sample Rate Support
To show the supported sample rates for a specific sound card codec, you can also inspect the codec details:
```bash
cat /proc/asound/card1/codec#0 | grep -i rates
```
This will output the supported sample rates for the codec associated with `card1`.
### Differentiating Between Cards
Accessing Card 1 (sof-hda-dsp)
```bash
cat /proc/asound/cards | grep -A 1 '^ 1 '
```
Accessing Card 2 (USB Audio Device)
```bash
cat /proc/asound/cards | grep -A 1 '^ 2 '
```
### Step 3: Testing audio inside QM
Inside QM, run the following command:
```bash
podman exec -it qm bash
bash-# podman ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
76dacaa9a89e quay.io/qm-images/audio:latest sleep infinity 7 hours ago Up 7 hours systemd-audio
bash-# podman exec -it systemd-audio bash
Execute the audio test within the nested container, and the sound will be output through the physical speakers of your computer—or, in this case, the car's multimedia soundbox.
bash-# speaker-test -D hw:1,0 -c 2 -r 48000
```
Params:
```bash
hw:1,0: sound card 1, device 0
-c 2: two channels (stereo)
-r 48000: sample rate of 48 kHz
```
## QM sub-package OCI Hooks
The QM sub-package OCI Hooks provides dynamic device access management for containers through OCI runtime hooks. This subpackage includes essential hooks that enable secure and flexible device sharing between the host system and containers with robust error handling and comprehensive testing.
### Components
The `qm-oci-hooks` subpackage includes:
- **qm-device-manager**: Dynamic device mounting hook that provides access to various hardware devices based on container annotations
- **wayland-client-devices**: Hook for GPU hardware acceleration access for Wayland client applications running as nested containers
### Supported Device Types
#### QM Device Manager
The `qm-device-manager` hook supports the following device types through container annotations:
| Device Type | Annotation | Devices Provided |
|-------------|------------|------------------|
| Audio | `org.containers.qm.device.audio=true` | `/dev/snd/*` (audio devices) |
| Video | `org.containers.qm.device.video=true` | `/dev/video*`, `/dev/media*` (cameras, video devices) |
| Input | `org.containers.qm.device.input=true` | `/dev/input/*` (keyboards, mice, touchpads) |
| TTYs | `org.containers.qm.device.ttys=true` | `/dev/tty0-7` (virtual terminals) |
| TTY USB | `org.containers.qm.device.ttyUSB=true` | `/dev/ttyUSB*` (USB TTY devices) |
| DVB | `org.containers.qm.device.dvb=true` | `/dev/dvb/*` (digital TV devices) |
| Radio | `org.containers.qm.device.radio=true` | `/dev/radio*` (radio devices) |
| Multi-seat Support | `org.containers.qm.wayland.seat=seat0` | Input devices, render devices, and display devices associated with the specified systemd-logind seat |
#### Wayland Client Devices
The `wayland-client-devices` hook supports:
| Functionality | Annotation | Devices Provided |
|---------------|------------|------------------|
| GPU Acceleration | `org.containers.qm.wayland-client.gpu=true` | GPU render devices (`/dev/dri/render*`) for hardware acceleration |
### Features
- **Dynamic Device Discovery**: Automatically discovers and mounts available devices at container startup
- **Annotation-Based Security**: Devices are only mounted when explicitly requested via annotations
- **Multi-seat Support**: Enables proper device access in systemd-logind multi-seat environments
- **Comprehensive Mock Device Support**: Full testing infrastructure with mock devices for all device types
- **GPU Acceleration**: Provides hardware acceleration for Wayland client applications
- **Comprehensive Logging**: All hooks provide detailed logging for monitoring and debugging:
- Device Manager: `/var/log/qm-device-manager.log`
- Wayland Client: `/var/log/qm-wayland-client-devices.log`
- **Runtime Flexibility**: No system restart required when adding device access to new containers
- **Lightweight Implementation**: Shell script-based hooks with minimal dependencies
### Building and Installing
```bash
git clone https://github.com/containers/qm.git && cd qm
make TARGETS=qm-oci-hooks subpackages
sudo dnf install rpmbuild/RPMS/noarch/qm-oci-hooks-*.noarch.rpm
```
### Usage Examples
#### Example 1: Serial communication with USB TTY devices
```bash
# Create a container with access to all USB TTY devices
cat > /etc/containers/systemd/serial-app.container << EOF
[Unit]
Description=Serial Communication Application
[Container]
Image=my-serial-app:latest
Annotation=org.containers.qm.device.ttyUSB=true
[Install]
WantedBy=default.target
EOF
```
#### Example 2: Multi-seat Wayland compositor with session devices
```bash
# Create a dropin for QM container to enable multi-seat support
mkdir -p /etc/containers/systemd/qm.container.d/
cat > /etc/containers/systemd/qm.container.d/wayland-seat.conf << EOF
[Container]
Annotation=org.containers.qm.wayland.seat=seat0
EOF
# Create a Wayland compositor container that runs inside QM
cat > /etc/qm/containers/systemd/wayland-compositor.container << EOF
[Unit]
Description=Wayland Compositor with Multi-seat Support
[Container]
Image=wayland-compositor:latest
Annotation=org.containers.qm.wayland.seat=seat0
[Install]
WantedBy=default.target
EOF
```
#### Example 3: Wayland client application with GPU acceleration
```bash
# Create a Wayland client container with GPU hardware acceleration
cat > /etc/qm/containers/systemd/gpu-app.container << EOF
[Unit]
Description=GPU-accelerated Application
[Container]
Image=my-gpu-app:latest
Annotation=org.containers.qm.wayland-client.gpu=true
[Install]
WantedBy=default.target
EOF
```
### Verification
To verify the hooks are installed and working:
```bash
# Check all OCI hook installations
ls -la /usr/share/containers/oci/hooks.d/
# Check hook executables
ls -la /usr/libexec/oci/hooks.d/
# Verify hook JSON configurations are valid
find /usr/share/containers/oci/hooks.d/ -name "*.json" -exec jq . {} \;
# View hook logs (all hooks provide comprehensive logging)
tail -f /var/log/qm-device-manager.log
tail -f /var/log/qm-wayland-client-devices.log
# Test device access with qm-device-manager
podman exec -it my-audio-app ls -la /dev/snd/
# Test GPU access with wayland-client-devices (if applicable)
podman exec -it gpu-app ls -la /dev/dri/
# Run hook tests (if source available)
cd oci-hooks && tox -e all
```
### Testing and Development
The OCI hooks include a comprehensive test suite for development and validation:
```bash
# Run all tests
cd oci-hooks && tox -e all
# Run specific test categories
tox -e unit # Unit tests only
tox -e integration # Integration tests only
tox -e performance # Performance tests only
# Run linting and formatting
tox -e lint # Code linting
tox -e format # Code formatting
# Test with mock devices (useful for CI environments)
FORCE_MOCK_DEVICES=true tox -e unit -- -k "mock_devices"
```
### OCI Hooks Specification and Documentation
The QM OCI hooks are implemented according to the [Open Container Initiative (OCI) Runtime Specification](https://github.com/opencontainers/runtime-spec).
#### OCI Hook Configuration Format
OCI hooks are configured using JSON files that define when and how the hooks should be executed. Each hook configuration follows the structure defined in the [OCI config schema](https://github.com/opencontainers/runtime-spec/blob/main/schema/config-schema.json).
**Key components of hook configuration:**
- **version**: OCI specification version (e.g., `"1.0.0"`)
- **hook**: Object defining the hook executable and arguments
- **when**: Object defining trigger conditions for the hook
- **stages**: Array of lifecycle stages when the hook should run
#### Hook Lifecycle Stages
According to the [OCI POSIX Platform Hooks specification](https://github.com/opencontainers/runtime-spec/blob/main/config.md#posix-platform-hooks), hooks can be executed at three stages:
1. **prestart**: Hooks called after the container process is spawned, but before the user-supplied command is executed
2. **poststart**: Hooks called after the user-supplied command is executed
3. **poststop**: Hooks called after the container process is terminated
QM hooks execution stages:
- `qm-device-manager`: Runs during **prestart** to mount devices before the container starts
- `wayland-client-devices`: Runs during **prestart** to provide GPU access before the container starts
#### Hook Input/Output Specification
OCI hooks receive container state information via **stdin** and communicate results via **stdout/stderr** and **exit codes**:
**Input (stdin)**: JSON object containing container state according to OCI spec:
```json
{
"ociVersion": "1.0.0",
"id": "container-id",
"status": "creating",
"pid": 1234,
"bundle": "/path/to/bundle",
"annotations": {
"org.containers.qm.device.audio": "true"
}
}
```
**Output**:
- **Exit code 0**: Success
- **Exit code non-zero**: Failure (container creation aborted)
- **stderr**: Error messages and diagnostics
- **stdout**: Hook output (typically empty for QM hooks)
#### Annotation Pattern Matching
QM hooks use regular expressions in their `when.annotations` configuration to match container annotations:
- `org\\.containers\\.qm\\.device\\.(audio|video|input|ttys|ttyUSB|dvb|radio)`: Matches device-specific annotations
- `org\\.containers\\.qm\\.wayland\\.seat`: Matches Wayland seat annotations with any value
- `org\\.containers\\.qm\\.wayland-client\\.gpu`: Matches GPU acceleration requests
#### Hook Installation Locations
QM hooks are installed in standard OCI locations:
- Hook executables: `/usr/libexec/oci/hooks.d/`
- Hook configurations: `/usr/share/containers/oci/hooks.d/`
- Hook libraries: `/usr/libexec/oci/lib/`
## QM sub-package ROS2
The QM sub-package ROS2 (a.k.a "The Robot Operating System" or middleware for robots) is widely used by open-source projects, enterprises, companies, edge env and government agencies, including NASA, to advance robotics and autonomous systems. Enabled by Quadlet in QM, ROS2 on top of QM provides a secure environment where robots can operate and communicate safely, benefiting from QM's "Freedom from Interference" frequently tested layer. This ensures robots can function without external interference, enhancing their reliability and security.
The types of robots compatible with this environment are extensive, ranging from medical devices and aerial drones to aqua drones and space rockets. ROS2 within QM supports high availability, meaning these robotic systems can maintain continuous operations, crucial for mission-critical and industrial applications. This versatility makes it ideal for environments that demand robust communication and operational safety, from healthcare and aerospace to underwater exploration and autonomous land vehicles.
How to test this env?
```bash
git clone https://github.com/containers/qm.git && cd qm
make TARGETS=ros2_rolling subpackages
sudo dnf install rpmbuild/RPMS/noarch/qm_ros2_rolling-0.6.7-1.fc40.noarch.rpm -y
sudo systemctl daemon-reload
sudo podman restart qm # if you have qm already running
Testing using talker and listener examples
$host> sudo podman exec -it qm bash
QM> . /opt/ros/jazzy/setup.bash # always replace jazz with the image ROS distro
QM> ros2 run demo_nodes_cpp talker &
QM> ros2 run demo_nodes_cpp listener
```
## QM sub-package KVM
The QM sub-package KVM includes drop-in configuration that enables the integration of Kernel-based Virtual Machine (KVM) management into the QM (Quality Management) container environment.
This configuration allows users to pull containerized kvm from [qm-images-repo](https://quay.io/repository/qm-images/kvm) and run it inside QM
There is also kvm.container which is installed as a service.
Below example step by step:
Step 1: clone QM repo, create rpm.
```bash
git clone https://github.com/containers/qm.git && cd qm
make TARGETS=kvm subpackages
```
Step 2: copy rpm to running machine
```bash
scp -oStrictHostKeyChecking=no -oUserKnownHostsFile=/dev/null -P 2222 rpmbuild/RPMS/noarch/qm-kvm-0.7.4-1.fc41.noarch.rpm root@127.0.0.1:/root/
```
Step 3: ssh machine install and verify
```bash
sudo dnf install ./qm-kvm-0.7.4-1.fc41.noarch.rpm
sudo systemctl restart qm # if you have qm already running
```
Step 4: verify, configuration exist
```bash
ls -ltr /etc/containers/systemd/qm.container.d/
total 12
-rw-r--r--. 1 root root 34 Jan 1 1970 publish-port.conf
-rw-r--r--. 1 root root 139 Jul 21 2023 qm_dropin_mount_bind_kvm.conf
ls -ltr /etc/qm/containers/systemd/
total 12
-rw-r--r--. 1 root root 91 Jan 1 1970 nginx.container
-rw-r--r--. 1 root root 188 Jul 21 2023 kvm.container
[root@localhost ~]# podman exec qm systemctl is-active kvm
active
[root@localhost ~]# podman exec -it qm sh
sh-5.1# ssh fedora@localhost -p 2226
[fedora@ibm-p8-kvm-03-guest-02 ~]$ grep ^NAME /etc/os-release
NAME="Fedora Linux"
```
### AutoSD install
Some notes related to installing qm on ostree AutoSD image
1. Check /var/qm size is larger then 1.5G
2. Installing in ostree images with dnf command, requires running rpm-ostree usroverlay
In case using aib schema to build your image, verify adding the following to build command
```bash
--define 'extra_rpms=["audit","dnf","python3-gobject"] qm_varpart_relative_size=0.5'
```

View File

@ -0,0 +1,17 @@
## Installing QM
The first step to getting started with QM is installation.
Fedora or CentOS:
On Fedora and CentOS-Stream systems (with EPEL repository enabled), QM can be directly installed via:
```bash
dnf install qm
```
## RPM Mirrors
Looking for a specific version of QM?
Search in the mirrors list below.
[CentOS Automotive SIG - qm package - noarch](https://mirror.stream.centos.org/SIGs/9-stream/automotive/aarch64/packages-main/Packages/q/)

View File

@ -0,0 +1,24 @@
# Virtualization: Android container with Quadlet
This is an example of an Android container running on top of kvm using quadlet and Wayland:
```console
$ cat ~/.config/containers/systemd/android.container
[Service]
Environment=WAYLAND_DISPLAY=wayland-0
[Container]
AddDevice=/dev/dri/renderD128
AddDevice=/dev/kvm
ContainerName=android
NoNewPrivileges=true
DropCapability=all
Environment=PULSE_SERVER=%t/pulse/native
Environment=WAYLAND_DISPLAY=${WAYLAND_DISPLAY}
Environment=XDG_RUNTIME_DIR=%t
Image=quay.io/slopezpa/qemu-aaos
PodmanArgs=--shm-size=5g
SecurityLabelDisable=true
Volume=%t:%t
```

View File

@ -0,0 +1,84 @@
# Using network modes with QM
## Basics: Network Modes in Podman
When running a container with Podman, you can specify the network mode using the `--network` flag. Two common options are `host` and `private`.
### Network=host
If you set `--network=host`, the container will use the host's network stack. This means the container will share the same network namespace as the host, and will be able to access the host's network interfaces, IP addresses, and ports.
In this mode, the container is not isolated from the host's network, and can potentially access sensitive network resources. This can be useful for certain use cases, such as running a container that needs to access a specific network interface or port on the host.
### Network=private (default)
By default, Podman uses the `private` network mode. This means that the container will have its own isolated network namespace, and will not be able to access the host's network interfaces, IP addresses, or ports.
In this mode, the container is isolated from the host's network, and can only communicate with other containers on the same network. This provides a higher level of security, as the container is not able to access sensitive network resources on the host.
### Security Implications
The reason `private` is the default network mode is due to security concerns. By isolating the container's network namespace, Podman prevents the container from accessing sensitive network resources on the host, such as:
* Host's network interfaces and IP addresses
* Host's ports and services
* Other containers on the host
This helps to prevent potential security vulnerabilities, such as:
* Container escape: a container accessing sensitive resources on the host
* Lateral movement: a container accessing other containers on the host
### Example
To illustrate the difference, consider the following example:
```bash
# Run a container with network=host
podman run -it --network=host fedora /bin/bash
# Run a container with network=private (default)
podman run -it --network=private fedora /bin/bash
```
In the first example, the container will share the host's network namespace, while in the second example, the container will have its own isolated network namespace.
For more information, see the [Podman Networking Tutorial](https://github.com/containers/podman/blob/main/docs/tutorials/basic_networking.md).
For network modes configuration example using quadlets, see [Quadlet Network Example](https://github.com/containers/qm/blob/main/docs/quadlet-examples/network/README.md).
## Quadlet example running host and private networks
Here is an example of running a network-test container using quadlets for both --network=host and --network=private. You should place this file either in /usr/share/containers/systemd/ or /etc/containers/systemd/
```console
/usr/share/containers/systemd/
/etc/containers/systemd/
```
For rootless users:
```console
$HOME/.config/containers/systemd/
```
Host Network
```console
# network-test.container
[Container]
ContainerName=network-test
Image=localhost/local-audio-image
Network=host
```
Private Network
```console
# network-test.container
[Container]
ContainerName=network-test
Image=localhost/local-audio-image
Network=private
```

View File

@ -0,0 +1,24 @@
# Changing variables in qm containers.conf
The `container.conf` file needs to be modified to allow pulling images larger than 1G from the repository on OStree images.
## Update container image_copy_tmp_dir if the image is an OStree
1. Create /var/qm/tmp.dir or differently named directory on host.
2. Create /etc/qm/containers/containers.conf.d or differently named directory on host.
3. Create and edit /etc/qm/containers/containers.conf.d/qm_image_tmp_dir.conf or differently named *.conf file and add the following lines:
[engine]
image_copy_tmp_dir="/var/tmp.dir"
## Sample code should look like this
<https://github.com/nsednev/qm/blob/3bbe302791ea5d0f271a1cc96ed6bce4d4b99de2/tests/ffi/common/prepare.sh#L76-L79>
By default image_copy_tmp_dir="/var/tmp".
Changing its default value to /var/tmp.dir will allow the container to pull images larger than 1G.
This is a work around and it should not be used constantly.
## Expected result
Containers on host will be able to pull images larger than 1G.

11
docs/docs/index.md Normal file
View File

@ -0,0 +1,11 @@
# QM
## QM is a containerized environment for running Functional Safety QM (Quality Management) software
The qm package sets up an isolated runtime environment for non-critical processes, managed through container tools and systemd. It is designed to ensure that these processes do not interfere with the host system, making it ideal for scenarios such as ASIL (Automotive Safety Integrity Level) separation.
QM runs as an exploded container—a persistent, containerized root filesystem mounted under /var/lib/qm/rootfs. It operates with its own instance of systemd, effectively creating a nested user space within its dedicated disk partition. This setup allows the system to isolate and control resource usage via cgroups, namespaces, and security constraints.
System-level tooling like Podman and systemd inside QM are fully independent from the host, so even container commands themselves are sandboxed. The environment is provisioned using Podman and configured with quadlet units, which streamline setup and lifecycle management.
Software installed inside the QM root is automatically isolated from the host. Developers can further segment workloads by using container tools inside QM to manage additional levels of containment for processes requiring extra isolation.

138
docs/docs/ipc.md Normal file
View File

@ -0,0 +1,138 @@
# Setting up IPC
## Table of Contents
1. [Setting up IPC](#setting-up-ipc)
1.1 [ASIL to QM IPC](#example-asil-to-qm-app)
- [`/etc/systemd/system/ipc_server.socket`](#etcsystemdsystemipc_serversocket)
- [`/etc/qm/containers/systemd/ipc_client.container`](#etcqmcontainerssystemdipc_clientcontainer)
- [`/etc/containers/systemd/ipc_server.container`](#etccontainerssystemdipc_servercontainer)
- [`/etc/containers/systemd/qm.container.d/10-extra-volume.conf`](#etccontainerssystemdqmcontainerd10-extra-volumeconf)
1.2 [QM to QM IPC](#example-qm-to-qm-app)
- [`/etc/qm/containers/systemd/ipc_client.container`](#etcqmcontainerssystemdipc_clientcontainer-1)
- [`/etc/qm/containers/systemd/ipc_server.container`](#etcqmcontainerssystemdipc_servercontainer)
---
In systems where **Automotive Safety Integrity Level (ASIL)** and **Quality Management (QM)**
components coexist, strict separation is enforced to maintain safety and security boundaries via
**SELinux (Security-Enhanced Linux)**, which labels processes and files with security contexts
to control their interactions.
**IPC (Inter-Process Communication)** between ASIL and QM components must be tightly controlled.
To comply with SELinux policies and avoid permission denials, any socket-based communication
between ASIL and QM domains should be established in the dedicated directory such as /run/ipc
with ipc_var_run_t file context. It serves as a secure bridge for cross-domain communication
while maintaining SELinux isolation.
On the other hand, **IPC between QM services** (e.g., two services or containers within the same QM domain)
can occur as well. Since these components share the same SELinux type and context, they are allowed to
communicate using standard Unix domain sockets located in /run. This approach simplifies internal QM
communication relies on container IPC without compromising the system's overall security posture. Such communication can be
orchestrated also using container orchestration patterns like **.pod (Podman pod definitions)** or
**.kube (Kubernetes pod manifests)**, which group related services in shared namespaces to support efficient
IPC within the same trust boundary.
## Example ASIL to QM app
<!-- markdownlint-disable MD024 -->
### /etc/systemd/system/ipc_server.socket
```console
[Unit]
Description=IPC Server Socket for asil-to-qm
[Socket]
ListenStream=%t/ipc/ipc.socket
SELinuxContextFromNet=yes
[Install]
WantedBy=sockets.target
```
### /etc/qm/containers/systemd/ipc_client.container
``` console
[Unit]
Description=Demo client service container (asil-to-qm)
[Container]
Image=quay.io/username/ipc-demo/ipc_client:latest
Network=none
Environment=SOCKET_PATH=/run/ipc/ipc.socket
Volume=/run/ipc/:/run/ipc/
SecurityLabelType=qm_container_ipc_t
[Service]
Restart=always
[Install]
WantedBy=multi-user.target
```
### /etc/containers/systemd/ipc_server.container
```console
[Unit]
Description=Demo server service container (asil-to-qm)
Requires=ipc_server.socket
After=ipc_server.socket
[Container]
Image=quay.io/username/ipc-demo/ipc_server
Network=none
Environment=SOCKET_PATH=/run/ipc/ipc.socket
Volume=/run/ipc/:/run/ipc/
SecurityLabelType=ipc_t
[Service]
Restart=always
Type=notify
[Install]
WantedBy=multi-user.target
```
### /etc/containers/systemd/qm.container.d/10-extra-volume.conf
```console
[Unit]
Requires=ipc_server
[Container]
Volume=/run/ipc/:/run/ipc/
```
## Example QM to QM app
### /etc/qm/containers/systemd/ipc_client.container
```console
[Unit]
Description=Demo client service container
Requires=ipc_server.service
After=ipc_server.service
[Container]
Image=quay.io/username/ipc-demo/ipc_client:latest
Network=none
Volume=/run/ipc.socket:/run/ipc.socket
SecurityLabelLevel=s0:c1,c2
[Service]
Restart=always
[Install]
WantedBy=multi-user.target
```
### /etc/qm/containers/systemd/ipc_server.container
```console
[Unit]
Description=Demo server service container
[Container]
Image=quay.io/username/ipc-demo/ipc_server:latest
Network=none
Volume=/run/:/run/
SecurityLabelLevel=s0:c1,c2
[Service]
Restart=always
Type=notify
[Install]
WantedBy=multi-user.target
```
<!-- markdownlint-disable MD024 -->

6
docs/docs/resources.md Normal file
View File

@ -0,0 +1,6 @@
# Additional Resources
- [Paving the Way for Uninterrupted Car Operations - DevConf Boston 2024](https://www.youtube.com/watch?v=jTrLqpw7E6Q)
- [Security - Sample Risk Analysis according to ISO26262](https://www.youtube.com/watch?v=jTrLqpw7E6Q&t=1268s)
- [ASIL and QM - Simulation and Service Monitoring using bluechi and podman](https://www.youtube.com/watch?v=jTrLqpw7E6Q&t=1680s)
- [Containers in a Car - DevConf.CZ 2023](https://www.youtube.com/watch?v=FPxka5uDA_4)

262
docs/docs/usage.md Normal file
View File

@ -0,0 +1,262 @@
# Using QM
This section describes how to interact with QM.
## Installing software inside QM partition
```bash
dnf --installroot /usr/lib/qm/rootfs/ install vim -y
```
## Removing software inside QM partition
```bash
dnf --installroot /usr/lib/qm/rootfs/ remove vim -y
```
## Copying files to QM partition
Please note: This process is only applicable for regular images.
OSTree images are read-only, and any files must be included during the build process.
Once this is understood, proceed by executing the following command on the host after
the QM package has been installed.
```bash
#host> cp file_to_be_copied /usr/lib/qm/rootfs/root
#host> podman exec -it qm bash
bash-5.1> ls /root
file_to_be_copied
```
## Listing QM service
```bash
[root@localhost ~]# systemctl status qm -l
● qm.service
Loaded: loaded (/usr/share/containers/systemd/qm.container; generated)
Active: active (running) since Sun 2024-04-28 22:12:28 UTC; 12s
ago
Main PID: 354 (conmon)
Tasks: 7 (limit: 7772)
Memory: 82.1M (swap max: 0B)
CPU: 945ms
CGroup: /qm.service
├─libpod-payload-a83253ae278d7394cb38e975535590d71de90a41157b547040
4abd6311fd8cca
│ ├─init.scope
│ │ └─356 /sbin/init
│ └─system.slice
│ ├─bluechi-agent.service
│ │ └─396 /usr/libexec/bluechi-agent
│ ├─dbus-broker.service
│ │ ├─399 /usr/bin/dbus-broker-launch --scope system
--audit
│ │ └─401 dbus-broker --log 4 --controller 9 --machin
e-id a83253ae278d7394cb38e975535590d7 --max-bytes 536870912 --max-fds 4096 --max
-matches 16384 --audit
```
## List QM container via podman
```console
# podman ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
a83253ae278d /sbin/init 38 seconds ago Up 38 seconds qm
```
## Extend QM quadlet managed by podman
QM quadlet file is shipped through rpm, refer the following file.
qm.container which is installed to /usr/share/containers/systemd/qm.container
Please refer `man quadlet` for the supported value and how to.
In case a change needed in quadlet file, do not update systemd/qm.container file
As per `man quadlet` do the following:
```console
if ! test -e /etc/containers/systemd/qm.container.d ; then
mkdir -p /etc/containers/systemd/qm.container.d
fi
cat > "/etc/containers/systemd/qm.container.d/expose-dev.conf" <<EOF
[Container]
# Expose host device /dev/net/tun
AddDevice=-/dev/net/tun
# In case parameter override needed, add empty value before the required key
Unmask=
Unmask=ALL
EOF
```
To verify the result use the following command:
```console
/usr/lib/systemd/system-generators/podman-system-generator --dryrun
```
Once the result is satisfied, apply the following
```console
systemctl daemon-reload
systemctl restart qm
systemctl is-active qm
active
```
## Managing CPU usage
Using the steps below, it's possible to manage CPU usage of the `qm.service` by modifying service attributes and utilizing drop-in files.
### Setting the CPUWeight attribute
Modifying the `CPUWeight` attribute affects the priority of the `qm.service`. A higher value prioritizes the service, while a lower value deprioritizes it.
Inspect the current CPUWeight value:
```bash
systemctl show -p CPUWeight qm.service
```
Set the CPUWeight value:
```bash
systemctl set-property qm.service CPUWeight=500
```
### Limiting CPUQuota
It's also possible to limit the percentage of the CPU allocated to the `qm.service` by defining `CPUQuota`. The percentage specifies how much CPU time the unit shall get at maximum, relative to the total CPU time available on one CPU.
Inspect the current `CPUQuota` value via the `CPUQuotaPerSecUSec` property:
```bash
systemctl show -p CPUQuotaPerSecUSec qm.service
```
Set the `CPUQuota` value of `qm.service` on the host using:
```bash
systemctl set-property qm.service CPUQuota=50%
```
Verify the `CPUQuota` drop in file has been created using the command below.
```bash
systemctl show qm.service | grep "DropInPath"
```
Expected output:
```bash
DropInPaths=/usr/lib/systemd/system/service.d/10-timeout-abort.conf /etc/systemd/system.control/qm.service.d/50-CPUQuota.conf
```
To test maxing out CPU usage and then inspect using the `top` command, follow these steps:
- Set the `CPUQuota` value of `qm.service` on the host using:
```bash
systemctl set-property qm.service CPUQuota=50%
```
- Execute this command to stress the CPU for 30 seconds:
```bash
podman exec qm timeout 30 dd if=/dev/zero of=/dev/null
```
- Observe the limited CPU consumption from the `qm.service`, as shown in the output of the command below:
```bash
top | head
```
Expected output:
```bash
PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND
1213867 root 20 0 2600 1528 1528 R 50.0 0.0 4:15.21 dd
3471 user 20 0 455124 7568 6492 S 8.3 0.0 1:43.64 ibus-en+
1 root 20 0 65576 37904 11116 S 0.0 0.1 0:40.00 systemd
```
## Connecting to QM container via podman
```console
# podman exec -it qm bash
bash-5.1#
```
## SSH guest CentOS Automotive Stream Distro
Make sure the CentOS Automotive Stream Distro Virtual Machine/Container is running with SSHD enabled
and permits ssh connection from root user.
Add **PermitRootLogin yes** into **sshd_config**
```bash
host> vi /etc/ssh/sshd_config
```
Restart systemctl restart sshd
```bash
host> systemctl restart sshd
```
Find the port the ssh is listening in the VM
```bash
host> netstat -na |more # Locate the port (2222 or 2223, etc)
```
Example connecting from the terminal to the Virtual Machine:
```bash
connect-to-VM-via-SSH> ssh root@127.0.0.1 \
-p 2222 \
-oStrictHostKeyChecking=no \
-oUserKnownHostsFile=/dev/null
```
## Check if HOST and Container are using different network namespace
### HOST
```console
[root@localhost ~]# ls -l /proc/self/ns/net
lrwxrwxrwx. 1 root root 0 May 1 04:33 /proc/self/ns/net -> 'net:[4026531840]'
```
### QM
```console
bash-5.1# ls -l /proc/self/ns/net
lrwxrwxrwx. 1 root root 0 May 1 04:33 /proc/self/ns/net -> 'net:[4026532287]'
```
## Debugging with podman in QM
```console
bash-5.1# podman --root /usr/share/containers/storage pull alpine
Error: creating runtime static files directory "/usr/share/containers/storage/libpod":
mkdir /usr/share/containers/storage: read-only file system
```
## Debugging with quadlet
Imagine a situation where you have a Quadlet container inside QM that isn't starting, and you're unsure why. The best approach is to log into the QM, run the ```quadlet --dryrun``` command, and analyze what's happening. Here's how you can troubleshoot the issue step by step.
```bash
$ sudo podman exec -it qm bash
bash-5.1# cd /etc/containers/systemd/
bash-5.1# ls
ros2.container
bash-5.1# /usr/libexec/podman/quadlet --dryrun
quadlet-generator[1068]: Loading source unit file /etc/containers/systemd/ros2.container
quadlet-generator[1068]: converting "ros2.container": unsupported key 'Command' in group 'Container' in /etc/containers/systemd/ros2.container
bash-5.1#
```
As you can see above, the error occurs because the Quadlet is attempting to use an unsupported key from the Service section in the Container group. Removing the unsupported key ```Command``` from ```ros2.container``` and then reloading or restarting the service should resolve the issue.

38
docs/mkdocs.yml Normal file
View File

@ -0,0 +1,38 @@
site_name: QM Documentation
repo_url: https://github.com/containers/qm
repo_name: qm
edit_uri: blob/main/docs/docs/
copyright: Copyright Contributors to the QM project
nav:
- Home: index.md
- Getting Started: getting_started.md
- Using QM: usage.md
- Setting up IPC: ipc.md
- How To:
- Android container: how_tos/android.md
- Using network modes with QM: how_tos/network.md
- Changing variables in QM: how_tos/qm_variables.md
- Experimental:
- QM Subpackages: experimental/subpackages.md
- Additional resources: resources.md
theme:
name: material
features:
- content.code.copy
- navigation.indexes
markdown_extensions:
- toc:
permalink: True
- sane_lists
- smarty
- admonition
- pymdownx.snippets:
base_path: ["docs"]
check_paths: True
- pymdownx.superfences:
- pymdownx.tabbed:
alternate_style: true

3
docs/requirements.txt Normal file
View File

@ -0,0 +1,3 @@
mkdocs>=1.3.0
mkdocs-material>=9.3.1
pymdown-extensions>=10.0.1

View File

@ -0,0 +1,5 @@
# Drop-in configuration for Podman to mount bind /dev/kvm from host to container
#
[Container]
AddDevice=-/dev/net/tun
AddDevice=-/dev/kvm

View File

@ -0,0 +1,42 @@
# Drop-in configuration for Podman to mount bind /dev/snd from host to container
#
# The ALSA sound architecture uses /dev/snd to represent sound hardware devices
# as special files in the filesystem. These files are typically accessed by
# user-space programs (like media players, audio recorders, or mixers) to
# interact with the sound hardware. Applications do not usually access these
# files directly. Instead, they use higher-level libraries (like PulseAudio,
# PipeWire, or ALSA's own libraries) to interface with the devices.
#
# +-------------------------------------------------------------+
# | User-Space Applications |
# |-------------------------------------------------------------|
# | Media Players | Audio Recorders | Audio Mixers |
# +-------------------------------------------------------------+
# | | |
# v v v
# +-------------------------------------------------------------+
# | High-Level Audio Libraries (User Space) |
# |-------------------------------------------------------------|
# | ALSA Libraries | PulseAudio | PipeWire |
# +-------------------------------------------------------------+
# | | |
# v v v
# +-------------------------------------------------------------+
# | /dev/snd (Special Files) |
# | ALSA Kernel Driver exposes sound devices as /dev/snd |
# +-------------------------------------------------------------+
# | | |
# v v v
# +-------------------------------------------------------------+
# | ALSA Kernel Sound Drivers (Hardware) |
# | Interfacing with Sound Cards and Audio Devices |
# +-------------------------------------------------------------+
# | | |
# v v v
# +-------------------------------------------------------------+
# | Sound Hardware (Speakers, Mics) |
# +-------------------------------------------------------------+
#
# qm_dropin_mount_bind_snd.conf
[Container]
Annotation=org.containers.qm.device.audio=true

View File

@ -0,0 +1,60 @@
# Drop-in configuration for Podman to mount bind /dev/videoX cameras devices
#
# In a typical vehicle system, cameras are connected to the car's onboard computer via a CAN bus
# (Controller Area Network), which transmits signals from the cameras to the cars system for real-time
# processing. This is commonly used for functions like parking assistance, lane-keeping, or 360-degree
# surround-view systems.
#
# However, it's possible to create a simulation environment using traditional hardware and open-source
# software, eliminating the need for actual car cameras or CAN bus integration. By using open-source
# tools like Podman containers and video processing libraries (such as GStreamer or FFmpeg), virtual
# cameras can be simulated. These tools allow developers to simulate the video signals typically
# produced by physical car cameras and routed through the CAN bus.
#
# In this setup, virtual devices (e.g., /dev/video0, /dev/video1) are mounted into a container and can
# provide simulated video streams that mimic real camera feeds. This allows automotive software to be
# developed and tested in a controlled environment, replicating the behavior of car cameras without
# needing access to the physical hardware or CAN bus.
#
# "/dev/video0:/dev/video0", # Front camera
# "/dev/video1:/dev/video1", # Back camera
#
# "/dev/video2:/dev/video2", # Power side view mirror camera (Right)
# "/dev/video3:/dev/video3", # Power side view mirror camera (Left)
#
# "/dev/video4:/dev/video4", # side car camera (Right)
# "/dev/video5:/dev/video5" # side car camera (Left)
#
# Camera System Layout (Top-Down View)
#
# ┌─────────────────────────────┐
# │ /dev/video0 │
# │ (Front Camera) │
# │ Primary forward-view camera│
# └────────────┬────────────────┘
# │
# ┌─────────────────────┴────────────────────────────────┐
# │ Vehicle Body (Top View) │
# │ │
# │ ┌─────────────────┐ ┌─────────────────┐ │
# │ │ /dev/video2 │ │ /dev/video3 │ │
# │ │ (Right Mirror) │ │ (Left Mirror) │ │
# │ │ Secondary camera│ │ Secondary camera│ │
# │ └─────────────────┘ └─────────────────┘ │
# │ │
# │ ┌─────────────────┐ ┌─────────────────┐ │
# │ │ /dev/video4 │ │ /dev/video5 │ │
# │ │ (Right Side) │ │ (Left Side) │ │
# │ │ Side-view camera│ │ Side-view camera│ │
# │ └─────────────────┘ └─────────────────┘ │
# └──────────────────────────────────────────────────────┘
# │
# ┌─────────────────────────────┐
# │ /dev/video1 │
# │ (Rear Camera) │
# │ Primary rear-view camera │
# └─────────────────────────────┘
#
#
[Container]
AddDevice=-/dev/video0

View File

@ -0,0 +1,4 @@
# Drop-in configuration for Podman to mount bind tty from host to container
#
[Container]
Annotation=org.containers.qm.device.ttys=true

View File

@ -0,0 +1,13 @@
# This configuration file was generated by qm-dropin sub-package:
# - qm-dropin-img-tempdir
#
# It configures the temporary directory used by the container engine
# for image copy operations. This setting is useful for performance
# optimizations or managing disk space.
#
# How it works?
#=================
# [engine] <- section
# image_copy_tmp_dir <- Specifies the directory for temporary image storage.
[engine]
image_copy_tmp_dir="/var/tmp.dir"

21
oci-hooks/lib/common.sh Normal file
View File

@ -0,0 +1,21 @@
#!/bin/bash
# Common Utility Library for OCI Hooks
# This file provides shared utility functions for all OCI hooks.
# Common logging function for OCI hooks
log() {
local level="$1"
shift
local message
message="$(date '+%Y-%m-%d %H:%M:%S') - ${HOOK_NAME:-oci-hook} - $level - $*"
# Write to log file if LOGFILE is set
if [[ -n "${LOGFILE:-}" ]]; then
echo "$message" >>"$LOGFILE"
fi
# Also write errors to stderr
if [[ "$level" == "ERROR" ]]; then
echo "$message" >&2
fi
}

View File

@ -0,0 +1,82 @@
#!/bin/bash
# Device Support Library for OCI Hooks
# This file provides standard device discovery functionality for OCI hooks.
# Source common utilities
# shellcheck source=./common.sh disable=SC1091
source "$(dirname "${BASH_SOURCE[0]}")/common.sh"
# Device discovery function using standard filesystem operations
discover_devices() {
local pattern="$1"
local device_type="$2"
# Extract directory path from pattern to check existence first
local dir_path=""
if [[ "$pattern" =~ find[[:space:]]+(/[^[:space:]]+) ]]; then
dir_path="${BASH_REMATCH[1]}"
fi
# Check if specific directory exists (for patterns that search specific dirs)
if [[ -n "$dir_path" && "$dir_path" != "/dev" ]]; then
if [[ ! -d "$dir_path" ]]; then
# Directory doesn't exist - return empty, not an error
return 0
fi
fi
# Normal device discovery
eval "$pattern" 2>/dev/null || true
}
# Get device information for a given device path
get_device_info() {
local device_path="$1"
if [[ ! -e "$device_path" ]]; then
return 1
fi
if [[ ! -c "$device_path" ]]; then
return 1
fi
local stat_output
if ! stat_output=$(stat -c "%F:%t:%T:%f:%u:%g" "$device_path" 2>/dev/null); then
return 1
fi
local major minor file_mode uid gid
IFS=':' read -r _ major minor file_mode uid gid <<<"$stat_output"
# Convert hex to decimal
major=$((0x$major))
minor=$((0x$minor))
file_mode=$((0x$file_mode))
# Determine device type
local device_type="c"
# Return colon-separated values
echo "$device_type:$major:$minor:$file_mode:$uid:$gid"
}
# Check if device directory exists
should_process_device_type() {
local device_type="$1"
local directory="$2"
# Process if the directory exists and is accessible
[[ -d "$directory" ]] 2>/dev/null
}
# GPU device discovery for wayland-client-devices
discover_gpu_devices() {
# Normal device discovery - check if directory exists first
if [[ -d "/dev/dri" ]]; then
find /dev/dri -type c \( -regex ".*/render.*" \) 2>/dev/null || true
else
# No GPU devices directory - return empty (not an error)
return 0
fi
}

View File

@ -0,0 +1,176 @@
#!/bin/bash
# Mock Device Support Library for OCI Hooks Testing
# This file provides device mocking functionality for testing OCI hooks
# without requiring actual system devices.
# Source common utilities
# shellcheck source=./common.sh disable=SC1091
source "$(dirname "${BASH_SOURCE[0]}")/common.sh"
# Device discovery function with test override support
discover_devices() {
local pattern="$1"
local device_type="$2"
# Check for test override environment variable
local override_var="TEST_MOCK_${device_type^^}_DEVICES"
local override_value="${!override_var:-}"
if [[ -n "$override_value" ]]; then
# Use test-provided mock devices
log "DEBUG" "Using mock $device_type devices: $override_value"
# Convert comma-separated devices to null-terminated individual paths
IFS=',' read -ra device_array <<<"$override_value"
for device in "${device_array[@]}"; do
printf '%s\0' "$device"
done
return
fi
# Extract directory path from pattern to check existence first
local dir_path=""
if [[ "$pattern" =~ find[[:space:]]+(/[^[:space:]]+) ]]; then
dir_path="${BASH_REMATCH[1]}"
fi
# Check if specific directory exists (for patterns that search specific dirs)
if [[ -n "$dir_path" && "$dir_path" != "/dev" ]]; then
if [[ ! -d "$dir_path" ]]; then
# Directory doesn't exist - return empty, not an error
return 0
fi
fi
# Normal device discovery fallback
eval "$pattern" 2>/dev/null || true
}
# Get device information - works with real temporary device files created by mknod
get_device_info() {
local device_path="$1"
# First try to get real device info (works if mknod succeeded)
if [[ -e "$device_path" && -c "$device_path" ]]; then
local stat_output
if stat_output=$(stat -c "%F:%t:%T:%f:%u:%g" "$device_path" 2>/dev/null); then
local major minor file_mode uid gid
IFS=':' read -r _ major minor file_mode uid gid <<<"$stat_output"
# Convert hex to decimal
major=$((0x$major))
minor=$((0x$minor))
file_mode=$((0x$file_mode))
# Determine device type
local device_type="c"
# Return colon-separated values
echo "$device_type:$major:$minor:$file_mode:$uid:$gid"
return 0
fi
fi
# If real device doesn't exist and we're in test mode, generate mock device info
if [[ "${FORCE_MOCK_DEVICES:-false}" == "true" || -n "${TEST_LOGFILE:-}" ]]; then
# Check if this path matches any of our test mock device patterns
local is_mock=false
for env_var in TEST_MOCK_AUDIO_DEVICES TEST_MOCK_VIDEO_DEVICES TEST_MOCK_INPUT_DEVICES \
TEST_MOCK_GPU_DEVICES TEST_MOCK_TTYUSB_DEVICES TEST_MOCK_DVB_DEVICES \
TEST_MOCK_RADIO_DEVICES TEST_MOCK_TTYS_DEVICES; do
if [[ -n "${!env_var:-}" ]]; then
IFS=',' read -ra mock_devices <<<"${!env_var}"
for mock_device in "${mock_devices[@]}"; do
if [[ "$mock_device" == "$device_path" ]]; then
is_mock=true
break 2
fi
done
fi
done
if [[ "$is_mock" == "true" ]]; then
# Generate mock device info based on device path patterns
local major minor file_mode=8624 uid=0 gid=0 # Default values
local device_type="c"
case "$device_path" in
*/snd/*)
major=116
minor=$((RANDOM % 20 + 1))
;; # ALSA devices
*/video*)
major=81
minor=$((RANDOM % 10))
;; # Video devices
*/input/*)
major=13
minor=$((RANDOM % 32))
;; # Input devices
*/dri/*)
major=226
minor=$((RANDOM % 10 + 128))
;; # DRI/GPU devices
*/ttyUSB*)
major=188
minor=$((RANDOM % 10))
;; # USB serial
*/dvb/*)
major=212
minor=$((RANDOM % 10))
;; # DVB devices
*/radio*)
major=81
minor=$((RANDOM % 10 + 64))
;; # Radio devices
*/tty[0-9]*)
major=4
minor=$((RANDOM % 10))
;; # TTY devices
*)
major=1
minor=$((RANDOM % 10))
;; # Fallback
esac
# Adjust gid for audio devices (usually audio group = 63)
if [[ "$device_path" == */snd/* ]]; then
gid=63
fi
echo "$device_type:$major:$minor:$file_mode:$uid:$gid"
return 0
fi
fi
# Neither real device nor mock - fail
return 1
}
# Check if device directory exists or we have mock devices for the type
should_process_device_type() {
local device_type="$1"
local directory="$2"
local override_var="TEST_MOCK_${device_type^^}_DEVICES"
local override_value="${!override_var:-}"
# Process if we have mock devices OR the directory exists and is accessible
[[ -n "$override_value" ]] || [[ -d "$directory" ]] 2>/dev/null
}
# GPU device discovery with mocking support for wayland-client-devices
discover_gpu_devices() {
if [[ -n "${TEST_MOCK_GPU_DEVICES:-}" ]]; then
# Use test-provided mock devices
log "DEBUG" "Using mock GPU devices: $TEST_MOCK_GPU_DEVICES"
echo "$TEST_MOCK_GPU_DEVICES" | tr ',' ' '
else
# Normal device discovery - check if directory exists first
if [[ -d "/dev/dri" ]]; then
find /dev/dri -type c \( -regex ".*/render.*" \) 2>/dev/null || true
else
# No GPU devices directory - return empty (not an error)
log "DEBUG" "No /dev/dri directory found - no GPU devices available"
return 0
fi
fi
}

View File

@ -0,0 +1,281 @@
# QM Device Manager OCI Hook
The QM Device Manager OCI Hook provides dynamic device access management for QM containers. This lightweight shell script hook replaces static drop-in configurations with a flexible, annotation-based approach to device mounting.
## Overview
The device manager hook allows containers to request specific device access through annotations. The hook dynamically discovers and mounts the requested devices at container creation time. It supports both device categories and Wayland seat-based device access.
## How Device Injection Works
The QM Device Manager hook operates during the OCI container **precreate** phase, intercepting container creation to dynamically inject device access. When QM starts a container with device annotations, the hook:
1. Discovers available devices on the host system based on annotation patterns
2. Validates device accessibility and permissions
3. Injects device access into the container's OCI specification via `linux.resources.devices[]`
4. Adds device mounts to make devices available inside the container
### OCI Device Injection Format
The hook modifies the container's OCI runtime specification to include device access rules:
```json
{
"linux": {
"resources": {
"devices": [
{
"allow": true,
"type": "c",
"major": 116,
"minor": 0,
"access": "rwm"
},
{
"allow": true,
"type": "c",
"major": 116,
"minor": 1,
"access": "rwm"
}
]
}
},
"mounts": [
{
"source": "/dev/snd/controlC0",
"destination": "/dev/snd/controlC0",
"type": "bind",
"options": ["bind", "rprivate"]
}
]
}
```
This ensures the container has both cgroup device access permissions and the actual device nodes mounted.
### Testing and Verification
The device injection process is comprehensively tested in the test suite:
- Device Discovery Tests (`test_qm_devices.py`): Verifies correct device discovery for all supported types
- Annotation Processing (`test_qm_validation.py`): Tests annotation parsing and validation
- Mock Device Support (`test_utils.py`): Provides mock device infrastructure for CI testing
- Integration Tests (`test_qm_performance.py`): End-to-end hook execution testing
Run tests to verify device injection:
```bash
cd oci-hooks && tox -e unit -- -k "device"
```
### Library Architecture
The QM Device Manager hook uses a modular library architecture for maintainability and testing:
#### Core Libraries
- `common.sh`: Shared logging and utility functions used across all OCI hooks
- `device-support.sh`: Production device discovery and management functions
- `mock-device-support.sh`: Testing-specific device simulation functions
#### Mock Device Support for Testing
The `mock-device-support.sh` library enables comprehensive testing without requiring actual hardware devices. It works by:
Environment Variable Control - Tests set environment variables like:
```bash
TEST_MOCK_AUDIO_DEVICES="/tmp/test_devices/snd/controlC0,/tmp/test_devices/snd/pcmC0D0p"
TEST_MOCK_VIDEO_DEVICES="/tmp/test_devices/video0,/tmp/test_devices/video1"
TEST_LOGFILE="/tmp/test.log" # Enables test mode
```
Mock Device Creation - Python test framework creates temporary device files:
```python
# In test_utils.py DeviceDetector class
device_path = Path("/tmp/test_devices/snd/controlC0")
device_path.parent.mkdir(parents=True, exist_ok=True)
device_path.touch() # Creates regular file as mock device
```
Hook Library Selection - The hook script automatically detects test mode and sources the appropriate library:
```bash
# In oci-qm-device-manager script
if [[ -n "${TEST_LOGFILE:-}" ]]; then
source /usr/libexec/oci/lib/mock-device-support.sh
else
source /usr/libexec/oci/lib/device-support.sh
fi
```
**NOTE**: mock device library is not supported in a productive environment.
Mock Functions - `mock-device-support.sh` overrides discovery functions to return test devices:
```bash
discover_audio_devices() {
if [[ -n "${TEST_MOCK_AUDIO_DEVICES:-}" ]]; then
echo "${TEST_MOCK_AUDIO_DEVICES}" | tr ',' '\n'
fi
}
get_device_info() {
local device_path="$1"
# Returns mock device info for regular files in test mode
echo "c 116:0" # Mock major:minor for audio devices
}
```
This architecture allows the same hook script to work with both real hardware devices in production and simulated devices in CI testing environments.
## Supported Device Types
### Traditional Device Categories
| Device Type | Annotation | Devices Mounted | Description |
|-------------|------------|-----------------|-------------|
| audio | `org.containers.qm.device.audio=true` | `/dev/snd/*` | ALSA sound devices |
| video | `org.containers.qm.device.video=true` | `/dev/video*`, `/dev/media*` | V4L2 video devices |
| input | `org.containers.qm.device.input=true` | `/dev/input/*` | Input devices (keyboard, mouse, etc.) |
| ttys | `org.containers.qm.device.ttys=true` | `/dev/tty0-7` | Virtual TTY devices for window managers |
| ttyUSB | `org.containers.qm.device.ttyUSB=true` | `/dev/ttyUSB*` | USB TTY devices for serial communication |
| dvb | `org.containers.qm.device.dvb=true` | `/dev/dvb/*` | DVB digital TV devices |
| radio | `org.containers.qm.device.radio=true` | `/dev/radio*` | Radio devices |
### Wayland Seat Support
| Annotation | Purpose | Description |
|------------|---------|-------------|
| `org.containers.qm.wayland.seat=<seat_name>` | Multi-seat support | Mounts devices associated with a specific Wayland seat (e.g., `seat0`) |
The Wayland seat functionality dynamically discovers and mounts devices associated with the specified seat using `loginctl seat-status`. This enables proper multi-seat support for Wayland environments where different users may be logged into different seats.
## Usage Examples
### Systemd Drop-In Files
1. Create a drop-in directory and file:
```bash
mkdir -p /etc/containers/systemd/qm.container.d/
```
2. Create a dropin file (e.g., `devices.conf`):
```ini
[Container]
Annotation=org.containers.qm.device.audio=true
Annotation=org.containers.qm.device.ttys=true
# Wayland seat support
Annotation=org.containers.qm.wayland.seat=seat0
```
### Generated Systemd Service
When using Quadlet (`.container` files), the systemd generator creates the actual `ExecStart` commands that execute `podman run`. You can preview these with:
```bash
# View generated systemd service commands
/usr/lib/systemd/system-generators/podman-system-generator --dryrun
# Check generated service files
ls -la /var/lib/systemd/generated/
cat /var/lib/systemd/generated/container-name.service
```
#### Example Generated Commands within QM
For a Quadlet container with device annotations:
Quadlet File (`/etc/containers/systemd/audio-app.container`):
```ini
[Unit]
Description=Audio Application Container
After=local-fs.target
[Container]
Image=my-audio-app:latest
Annotation=org.containers.qm.device.audio=true
Annotation=org.containers.qm.device.video=true
Exec=sleep infinity
[Install]
WantedBy=default.target
```
Generated ExecStart Command:
```bash
ExecStart=/usr/bin/podman run \
--cidfile=%t/%N.cid \
--cgroups=split \
--replace \
--rm -d \
--sdnotify=container \
--name=audio-app \
--annotation=org.containers.qm.device.audio=true \
--annotation=org.containers.qm.device.video=true \
localhost/qm/my-audio-app:latest sleep infinity
```
When this service starts, the `qm-device-manager` hook intercepts the container creation and dynamically adds device mounts like:
- `--device=/dev/snd/controlC0:/dev/snd/controlC0`
- `--device=/dev/snd/pcmC0D0p:/dev/snd/pcmC0D0p`
- `--device=/dev/video0:/dev/video0`
## Logging
The hook logs activity to `/var/log/qm-device-manager.log` for debugging and monitoring:
```bash
# View hook activity
tail -f /var/log/qm-device-manager.log
# Check device discovery for a specific container
grep "audio" /var/log/qm-device-manager.log
# Check Wayland seat processing
grep "Wayland seat" /var/log/qm-device-manager.log
```
## Security Considerations
- Only devices that exist on the host are mounted
- Device permissions are preserved from the host
- Hook validates device accessibility before mounting
- Annotation-based activation prevents accidental device exposure
- Wayland seat integration respects systemd-logind seat assignments
## Troubleshooting
### Device Not Available
If a requested device is not mounted:
1. Check if the device exists on the host: `ls -la /dev/snd/`
2. Verify the annotation syntax: `org.containers.qm.device.audio=true`
3. Check hook logs: `grep ERROR /var/log/qm-device-manager.log`
4. Ensure the device is accessible: `test -c /dev/snd/controlC0`
### Wayland Seat Issues
If Wayland seat devices are not mounted:
1. Check seat status: `loginctl seat-status seat0`
2. Verify seat annotation: `org.containers.qm.wayland.seat=seat0`
3. Check systemd-logind service: `systemctl status systemd-logind`
4. Review seat logs: `grep "seat0" /var/log/qm-device-manager.log`
### Hook Not Triggering
If the hook is not being called:
1. Verify hook installation: `ls -la /usr/libexec/oci/hooks.d/`
2. Check hook configuration: `cat /usr/share/containers/oci/hooks.d/oci-qm-device-manager.json`
3. Validate annotation pattern matching
4. Check podman/crun OCI hook support

View File

@ -0,0 +1,391 @@
#!/bin/bash
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
# QM Device Manager OCI Hook
#
# This hook dynamically manages device access for QM containers based on annotations.
# It replaces the static drop-in configurations from individual subpackages with
# dynamic device mounting based on container annotations.
#
# Supported devices:
# - audio: /dev/snd/* (ALSA sound devices)
# - video: /dev/video*, /dev/media* (V4L2 video devices)
# - input: /dev/input/* (input devices like keyboards, mice)
# - ttys: /dev/tty0-7 (virtual TTY devices for window managers)
# - ttyUSB: /dev/ttyUSB* (USB TTY devices for serial communication)
# - dvb: /dev/dvb/* (DVB digital TV devices)
# - radio: /dev/radio* (radio devices)
#
# Supported device annotations:
# - org.containers.qm.device.audio=true # /dev/snd/* (ALSA sound devices)
# - org.containers.qm.device.video=true # /dev/video*, /dev/media* (V4L2 video devices)
# - org.containers.qm.device.input=true # /dev/input/* (input devices)
# - org.containers.qm.device.ttys=true # /dev/tty0-7 (virtual TTY devices)
# - org.containers.qm.device.ttyUSB=true # /dev/ttyUSB* (USB TTY devices)
# - org.containers.qm.device.dvb=true # /dev/dvb/* (DVB digital TV devices)
# - org.containers.qm.device.radio=true # /dev/radio* (radio devices)
#
# Supported Wayland annotations:
# - org.containers.qm.wayland.seat=<seat_name> # Devices for specific systemd-logind seat
set -euo pipefail
# Source common utilities and appropriate device support library
SCRIPT_DIR="$(dirname "${BASH_SOURCE[0]}")"
# shellcheck source=../lib/common.sh disable=SC1091
source "${SCRIPT_DIR}/../lib/common.sh"
if [[ -n "${TEST_LOGFILE:-}" ]]; then
# Test mode - use mock device support
# shellcheck source=../lib/mock-device-support.sh disable=SC1091
source "${SCRIPT_DIR}/../lib/mock-device-support.sh"
else
# Normal mode - use standard device support
# shellcheck source=../lib/device-support.sh disable=SC1091
source "${SCRIPT_DIR}/../lib/device-support.sh"
fi
# Configuration
LOGFILE="${TEST_LOGFILE:-/var/log/qm-device-manager.log}"
# shellcheck disable=SC2034 # Used by log() function in device-support.sh
HOOK_NAME="qm-device-manager"
# Process input devices with optional filtering and different output modes
process_input_devices() {
local mode="$1" # "direct" or "collect"
local spec_json="$2" # current spec (for direct mode)
local devname_list_var="$3" # variable name for device list (for collect mode)
local filter_pattern="${4:-}" # optional regex filter
local log_prefix="${5:-input}" # log message prefix
local device_count=0
if [[ ! -d "/dev/input" && -z "${TEST_LOGFILE:-}" ]]; then
if [[ "$mode" == "direct" ]]; then
log "INFO" "Added $device_count $log_prefix devices (no /dev/input directory)"
echo "$spec_json"
fi
return 0
fi
if [[ "$mode" == "collect" ]]; then
# For collect mode, we need to use nameref to modify the array
local -n devname_list_ref="$devname_list_var"
fi
while IFS= read -r -d '' device_path; do
# Apply filter if provided
if [[ -n "$filter_pattern" ]] && [[ ! "$device_path" =~ $filter_pattern ]]; then
continue
fi
if [[ "$mode" == "direct" ]]; then
# Add device directly to spec
spec_json=$(add_device_to_spec "$spec_json" "$device_path")
((device_count++))
elif [[ "$mode" == "collect" ]]; then
# Add device to collection list
devname_list_ref+=("$device_path")
log "INFO" "Adding $log_prefix device: $device_path"
((device_count++))
fi
done < <(discover_devices "find /dev/input -type c -print0" "input")
if [[ "$mode" == "direct" ]]; then
log "INFO" "Added $device_count $log_prefix devices"
echo "$spec_json"
fi
}
# Add device to OCI spec using jq
add_device_to_spec() {
local spec_json="$1"
local device_path="$2"
local add_resources="${3:-false}"
local device_info major minor file_mode uid gid device_type
if ! device_info=$(get_device_info "$device_path"); then
log "WARNING" "Failed to get device info for $device_path"
echo "$spec_json"
return
fi
IFS=':' read -r device_type major minor file_mode uid gid <<<"$device_info"
log "INFO" "Adding device: $device_path (type=$device_type, major=$major, minor=$minor)"
# Ensure .linux.devices array exists
local temp_spec
if ! temp_spec=$(echo "$spec_json" | jq --compact-output 'if .linux.devices == null then .linux.devices = [] else . end' 2>/dev/null); then
log "ERROR" "Failed to ensure .linux.devices array exists for $device_path"
echo "$spec_json"
return
fi
# Add device if it doesn't already exist
local result
if ! result=$(echo "$temp_spec" | jq --compact-output \
--arg path "$device_path" \
--arg type "$device_type" \
--argjson major "$major" \
--argjson minor "$minor" \
--argjson fileMode "$file_mode" \
--argjson uid "$uid" \
--argjson gid "$gid" \
'if (.linux.devices | map(.path) | index($path)) == null then .linux.devices += [{"path": $path, "type": $type, "major": $major, "minor": $minor, "fileMode": $fileMode, "uid": $uid, "gid": $gid}] else . end' 2>/dev/null); then
log "ERROR" "Failed to add device $device_path to spec"
echo "$temp_spec" # Return the spec with array at least initialized
return
fi
# Add device resources if requested (for Wayland devices)
if [[ "$add_resources" == "true" ]]; then
if ! result=$(echo "$result" | jq --compact-output \
--arg type "$device_type" \
--argjson major "$major" \
--argjson minor "$minor" \
'if .linux.resources == null then .linux.resources = {} else . end |
if .linux.resources.devices == null then .linux.resources.devices = [] else . end |
if (.linux.resources.devices | map(select(.type == $type and .major == $major and .minor == $minor)) | length) == 0 then
.linux.resources.devices += [{"allow": true, "type": $type, "major": $major, "minor": $minor, "access": "rwm"}]
else . end' 2>/dev/null); then
log "WARNING" "Failed to add device resources for $device_path, continuing with device only"
else
log "INFO" "Added device resources for: $device_path"
fi
fi
echo "$result"
}
# Process device annotations (org.containers.qm.device.*)
process_device_annotation() {
local spec_json="$1"
local device_type="$2"
log "INFO" "Processing device type: $device_type"
case "$device_type" in
"audio")
# ALSA sound devices
local device_count=0
if should_process_device_type "audio" "/dev/snd"; then
while IFS= read -r -d '' device_path; do
spec_json=$(add_device_to_spec "$spec_json" "$device_path")
((device_count++))
done < <(discover_devices "find /dev/snd -type c -print0" "audio")
fi
log "INFO" "Added $device_count audio devices"
;;
"video")
# V4L2 video devices
local device_count=0
while IFS= read -r -d '' device_path; do
spec_json=$(add_device_to_spec "$spec_json" "$device_path")
((device_count++))
done < <(discover_devices "find /dev -maxdepth 1 \\( -name \"video*\" -o -name \"media*\" \\) -type c -print0" "video")
log "INFO" "Added $device_count video devices"
;;
"input")
# Input devices
spec_json=$(process_input_devices "direct" "$spec_json" "" "" "input")
;;
"ttys")
# Virtual TTY devices (tty0-7)
local device_count=0
while IFS= read -r -d '' device_path; do
spec_json=$(add_device_to_spec "$spec_json" "$device_path")
((device_count++))
done < <(discover_devices "find /dev -maxdepth 1 -name 'tty[0-7]' -type c -print0" "ttys")
log "INFO" "Added $device_count TTY devices"
;;
"ttyUSB")
# USB TTY devices
local device_count=0
while IFS= read -r -d '' device_path; do
spec_json=$(add_device_to_spec "$spec_json" "$device_path")
((device_count++))
done < <(discover_devices "find /dev -maxdepth 1 -name \"ttyUSB*\" -type c -print0" "ttyUSB")
log "INFO" "Added $device_count USB TTY devices"
;;
"dvb")
# DVB digital TV devices
local device_count=0
if should_process_device_type "dvb" "/dev/dvb"; then
while IFS= read -r -d '' device_path; do
spec_json=$(add_device_to_spec "$spec_json" "$device_path")
((device_count++))
done < <(discover_devices "find /dev/dvb -type c -print0" "dvb")
fi
log "INFO" "Added $device_count DVB devices"
;;
"radio")
# Radio devices
local device_count=0
while IFS= read -r -d '' device_path; do
spec_json=$(add_device_to_spec "$spec_json" "$device_path")
((device_count++))
done < <(discover_devices "find /dev -maxdepth 1 -name \"radio*\" -type c -print0" "radio")
log "INFO" "Added $device_count radio devices"
;;
*)
log "WARNING" "Unknown device type: $device_type"
;;
esac
echo "$spec_json"
}
# Process Wayland seat annotation (org.containers.qm.wayland.seat)
process_wayland_seat() {
local spec_json="$1"
local seat_name="$2"
log "INFO" "Processing Wayland seat: $seat_name"
local device_count=0
local devname_list=()
# Get devices associated with the systemd-logind seat
if command -v loginctl >/dev/null 2>&1; then
local seat_devices
if seat_devices=$(loginctl seat-status "$seat_name" 2>/dev/null | grep -oP '/sys\S+'); then
log "INFO" "Found seat system devices for $seat_name"
while IFS= read -r device; do
if [[ -n "$device" ]]; then
local devname
if devname=$(udevadm info -x "$device" 2>/dev/null | grep -oP '^E: DEVNAME=\K.*'); then
if [[ -n "$devname" && -e "$devname" ]]; then
devname_list+=("$devname")
log "INFO" "Found seat device: $devname"
fi
fi
fi
done <<<"$seat_devices"
else
log "WARNING" "No devices found for seat $seat_name or seat does not exist"
fi
else
log "WARNING" "loginctl not available, cannot query seat devices"
fi
# Add common input devices
process_input_devices "collect" "" "devname_list" "/dev/input/(event[0-9]+|mice[0-9]*|mouse[0-9]+)$" "input"
# Add GPU render devices
if [[ -d "/dev/dri" ]]; then
while IFS= read -r -d '' device_path; do
if [[ "$device_path" =~ /dev/dri/render.* ]]; then
devname_list+=("$device_path")
log "INFO" "Adding render device: $device_path"
fi
done < <(discover_devices "find /dev/dri -type c -name \"render*\" -print0" "gpu")
fi
# Add all devices to spec with resources
for device_path in "${devname_list[@]}"; do
spec_json=$(add_device_to_spec "$spec_json" "$device_path" "true")
((device_count++))
done
log "INFO" "Added $device_count Wayland seat devices for $seat_name"
echo "$spec_json"
}
# Main function
main() {
local spec_json
local annotations
local total_devices=0
# Read OCI spec from stdin
if ! spec_json=$(cat); then
log "ERROR" "Failed to read OCI spec from stdin"
exit 1
fi
# Ensure linux section exists
if ! echo "$spec_json" | jq -e '.linux' >/dev/null 2>&1; then
spec_json=$(echo "$spec_json" | jq '.linux = {}')
fi
# Get all QM-related annotations
annotations=$(echo "$spec_json" | jq -r '.annotations // {} | to_entries[] | select(.key | startswith("org.containers.qm.")) | "\(.key)=\(.value)"' 2>/dev/null || true)
if [[ -z "$annotations" ]]; then
log "INFO" "No QM device annotations found"
echo "$spec_json"
return 0
fi
log "INFO" "Processing QM device annotations"
# Process each annotation
while IFS= read -r annotation; do
if [[ -z "$annotation" ]]; then
continue
fi
# Extract annotation key and value
annotation_key="${annotation%%=*}"
annotation_value="${annotation#*=}"
log "INFO" "Processing annotation: $annotation"
case "$annotation_key" in
"org.containers.qm.device."*)
# Traditional device annotation
device_type="${annotation_key#org.containers.qm.device.}"
# Skip if value is not true/1/yes
if [[ ! "$annotation_value" =~ ^(true|1|yes)$ ]]; then
log "INFO" "Skipping device annotation with invalid value: $annotation"
continue
fi
spec_json=$(process_device_annotation "$spec_json" "$device_type" "$annotation_value")
;;
"org.containers.qm.wayland.seat")
# Wayland seat annotation
if [[ -n "$annotation_value" && "$annotation_value" != "null" ]]; then
spec_json=$(process_wayland_seat "$spec_json" "$annotation_value")
else
log "INFO" "Skipping Wayland seat annotation with empty value"
fi
;;
*)
log "INFO" "Skipping unknown QM annotation: $annotation_key"
;;
esac
done <<<"$annotations"
# Count total devices added
total_devices=$(echo "$spec_json" | jq '.linux.devices // [] | length' 2>/dev/null || echo "0")
log "INFO" "Total devices in spec: $total_devices"
# Output the modified spec
echo "$spec_json"
log "INFO" "QM Device Manager hook completed successfully"
}
# Ensure log file exists
mkdir -p "$(dirname "$LOGFILE")"
touch "$LOGFILE"
# Run main function
main "$@"

View File

@ -0,0 +1,13 @@
{
"version": "1.0.0",
"hook": {
"path": "/usr/libexec/oci/hooks.d/oci-qm-device-manager"
},
"when": {
"annotations": {
"^org\\.containers\\.qm\\.device\\..*$": "^.*$",
"^org\\.containers\\.qm\\.wayland\\.seat": "^.*$"
}
},
"stages": ["precreate"]
}

68
oci-hooks/tests/.gitignore vendored Normal file
View File

@ -0,0 +1,68 @@
# Virtual environments
venv/
env/
.venv/
.env/
# Tox environments and cache
.tox/
.tox-*/
# Test reports and artifacts
reports/
.pytest_cache/
.coverage
htmlcov/
.nyc_output/
# Python cache and bytecode
__pycache__/
*.py[cod]
*$py.class
*.so
# Distribution / packaging
.Python
build/
develop-eggs/
dist/
downloads/
eggs/
.eggs/
lib/
lib64/
parts/
sdist/
var/
wheels/
share/python-wheels/
*.egg-info/
.installed.cfg
*.egg
MANIFEST
# IDEs and editors
.vscode/
.idea/
*.swp
*.swo
*~
# OS generated files
.DS_Store
.DS_Store?
._*
.Spotlight-V100
.Trashes
ehthumbs.db
Thumbs.db
# Temporary files
*.tmp
*.temp
/tmp/
.tmp/
# Logs
*.log
logs/

50
oci-hooks/tests/.pylintrc Normal file
View File

@ -0,0 +1,50 @@
[MAIN]
# Specify a score threshold to be exceeded before program exits with error
fail-under=10.0
# Use multiple processes to speed up Pylint
jobs=1
# Allow loading of arbitrary C extensions
unsafe-load-any-extension=no
[MESSAGES CONTROL]
# Disable specific warnings that are common/acceptable in test files
disable=
# Import related (pytest/test dependencies are OK)
import-error,
# Test-specific patterns
unused-argument, # Fixtures often have unused parameters
redefined-outer-name, # Fixture names often match test parameters
unused-variable, # Test outputs not always used
inconsistent-return-statements, # pytest.fail() is intentional pattern
# Less critical for tests
too-few-public-methods,
too-many-arguments,
too-many-locals,
duplicate-code, # Some duplication in tests is acceptable
# File organization
wrong-import-order, # Less critical in test files
# Naming
invalid-name, # Test method names can be long and descriptive
[DESIGN]
# Maximum number of arguments for function / method
max-args=8
# Maximum number of locals for function / method body
max-locals=20
[SIMILARITIES]
# Minimum lines number of a similarity
min-similarity-lines=10
[BASIC]
# Naming style matching correct function names (relaxed for tests)
function-rgx=[a-z_][a-z0-9_]{2,50}$
# Naming style matching correct method names (relaxed for tests)
method-rgx=[a-z_][a-z0-9_]{2,50}$
# Naming style matching correct class names
class-rgx=[A-Z_][a-zA-Z0-9]+$

107
oci-hooks/tests/README.md Normal file
View File

@ -0,0 +1,107 @@
# OCI Hooks Unit Tests
Simple unit tests for QM OCI hooks using pytest and tox.
## Quick Start
```bash
# Set up virtual environment
cd oci-hooks
python -m venv .venv
source .venv/bin/activate # Linux
# Install dependencies
pip install -r requirements.txt
# Install tox
pip install tox
# Run unit tests
tox -e unit
```
## Test Structure
### Test Files
- `test_qm_device_manager.py` - Tests for the unified device manager hook
- `test_wayland_client_devices.py` - Tests for the Wayland client GPU hook
### Test Categories
- **Unit tests**: Fast tests with no external dependencies
- **Integration tests**: Tests that may require system resources
- **Performance tests**: Tests with timing requirements
## Running Tests
### Using Tox
```bash
tox -e all # Run all tests
tox -e lint # Check code formatting for python and shell
tox -e format # Auto-format code with black
```
### Direct Pytest
If you prefer to avoid tox, you can run pytest directly:
```bash
# Set up virtual environment
python -m venv .venv
source .venv/bin/activate # Linux
# Install dependencies
pip install -r requirements.txt
# Run tests
pytest -m unit --tb=short -v # Unit tests only
pytest test_qm_device_manager.py # Specific test file
```
## CI/CD Integration
Tests run automatically in GitHub Actions on:
- Push to `oci-hooks/**` paths
- Pull requests affecting `oci-hooks/**` paths
Matrix testing across Python versions 3.9-3.12.
## Development Workflow
1. **Make changes** to OCI hook scripts or tests
2. **Run tests locally**: `tox -e unit`
3. **Check code quality**: `tox -e lint`
4. **Auto-format if needed**: `tox -e format`
5. **Fix any failures** before committing
6. **Push changes** - CI will run full test suite
## Troubleshooting
### Permission Issues
If hooks fail with permission errors, ensure scripts are executable:
```bash
chmod +x ../qm-device-manager/oci-qm-device-manager
chmod +x ../wayland-client-devices/oci-qm-wayland-client-devices
```
### Missing Dependencies
```bash
# For tox
pip install tox
# For direct pytest
pip install -r requirements.txt
```
### Test Environment
Tests use temporary log files to avoid permission issues:
- Set `TEST_LOGFILE` environment variable for custom log location
- Default: `/tmp/test-oci-hooks.log` for test runs

View File

@ -0,0 +1,98 @@
"""Pytest configuration and fixtures for OCI hooks testing."""
import os
import tempfile
from pathlib import Path
import pytest
from device_utils import DeviceCounter, TempDevices
from test_utils import (
HookRunner,
OciSpecValidator,
LogChecker,
)
@pytest.fixture(scope="session")
def test_env():
"""Set up test environment with temporary log files."""
with tempfile.TemporaryDirectory(prefix="oci_hooks_test_") as temp_dir:
env = os.environ.copy()
env["TEST_LOGFILE"] = os.path.join(temp_dir, "test-hook.log")
yield {
"env": env,
"log_file": env["TEST_LOGFILE"],
"temp_dir": temp_dir,
}
@pytest.fixture
def hook_runner(test_env):
"""Create a HookRunner instance with test environment and hook paths."""
yield HookRunner(test_env["env"])
@pytest.fixture
def oci_spec_validator():
"""Provide validator for OCI specification JSON."""
return OciSpecValidator.validate
@pytest.fixture
def sample_specs():
"""Sample OCI specifications for testing."""
yield {
"audio_device": {
"annotations": {"org.containers.qm.device.audio": "true"},
"linux": {},
},
"multiple_devices": {
"annotations": {
"org.containers.qm.device.audio": "true",
"org.containers.qm.device.input": "true",
"org.containers.qm.device.ttys": "true",
},
"linux": {},
},
"wayland_seat": {
"annotations": {"org.containers.qm.wayland.seat": "seat0"},
"linux": {},
},
"wayland_gpu": {
"annotations": {"org.containers.qm.wayland-client.gpu": "true"},
"linux": {},
},
"combined": {
"annotations": {
"org.containers.qm.device.audio": "true",
"org.containers.qm.wayland.seat": "seat0",
},
"linux": {},
},
"invalid_device": {
"annotations": {"org.containers.qm.device.audio": "false"},
"linux": {},
},
}
@pytest.fixture
def log_checker(test_env):
"""Check hook log files for expected content."""
return LogChecker(test_env["log_file"])
@pytest.fixture
def device_counter():
"""Fixture providing device counting utilities."""
return DeviceCounter
@pytest.fixture
def temp_devices():
"""Fixture providing on-demand temporary device creation."""
with tempfile.TemporaryDirectory(prefix="test_devices_") as temp_dir:
temp_path = Path(temp_dir)
yield TempDevices(temp_path)

View File

@ -0,0 +1,223 @@
"""Device testing utilities for OCI hooks."""
import os
import stat
from dataclasses import dataclass, field
from pathlib import Path
from typing import Dict, Any, Optional, List
class DeviceCounter:
"""Helper class for counting devices in OCI specifications."""
@staticmethod
def count_devices(
spec: Dict[str, Any], device_pattern: Optional[str] = None
) -> int:
"""Count devices in OCI spec, optionally filtered by path pattern."""
devices = spec.get("linux", {}).get("devices", [])
if device_pattern is None:
return len(devices)
return len([d for d in devices if device_pattern in d.get("path", "")])
@staticmethod
def count_resources(spec: Dict[str, Any]) -> int:
"""Count device resources in OCI spec."""
resources = (
spec.get("linux", {}).get("resources", {}).get("devices", [])
)
return len(resources)
@staticmethod
def has_device_path(spec: Dict[str, Any], path: str) -> bool:
"""Check if OCI spec contains a device with specific path."""
devices = spec.get("linux", {}).get("devices", [])
return any(d.get("path") == path for d in devices)
@dataclass
class DeviceDetector:
"""Class for detecting real devices for testing."""
paths: List[str] = field(default_factory=list)
expected_count: int = 0
def mock_devices(self, device_type) -> Optional[Dict[str, str]]:
"""Mock devices for testing."""
return {device_type: ",".join(self.paths)}
class TempDevices:
"""Class for creating temporary device files on-demand for testing."""
def __init__(self, temp_path: Path):
"""Initialize TempDevices with temporary path."""
self.temp_path = temp_path
self._created_devices = {}
# Create base directory structure
for subdir in ["snd", "dri", "input", "dvb"]:
(self.temp_path / subdir).mkdir(exist_ok=True)
def _create_device(
self, device_path: Path, major: int, minor: int
) -> Path:
"""Create device node with mknod if possible, fall back to env vars."""
device_path.parent.mkdir(parents=True, exist_ok=True)
if os.environ.get("FORCE_MOCK_DEVICES", "false").lower() != "true":
try:
# Try to create real device nodes when not forced
os.mknod(
device_path, stat.S_IFCHR | 0o600, os.makedev(major, minor)
)
except OSError:
# Fallback to regular files if mknod fails
device_path.touch()
else:
# Create regular files when forced to use mock mode
device_path.touch()
return device_path
def _set_mock_env_for_devices(self, device_type: str, devices: List[Path]):
"""Set mock environment variables for device discovery."""
env_var = f"TEST_MOCK_{device_type.upper()}_DEVICES"
os.environ[env_var] = ",".join(str(d) for d in devices)
def get_audio_devices(self) -> DeviceDetector:
"""Get audio device paths for testing."""
if "audio" not in self._created_devices:
devices = [
self._create_device(
self.temp_path / "snd" / "controlC0", 116, 0
),
self._create_device(
self.temp_path / "snd" / "pcmC0D0p", 116, 24
),
]
self._created_devices["audio"] = devices
self._set_mock_env_for_devices("audio", devices)
device_paths = [str(d) for d in self._created_devices["audio"]]
return DeviceDetector(
paths=device_paths, expected_count=len(device_paths)
)
def get_video_devices(self) -> DeviceDetector:
"""Get video device paths for testing."""
if "video" not in self._created_devices:
devices = [
self._create_device(self.temp_path / "video0", 81, 0),
self._create_device(self.temp_path / "video1", 81, 1),
]
self._created_devices["video"] = devices
self._set_mock_env_for_devices("video", devices)
device_paths = [str(d) for d in self._created_devices["video"]]
return DeviceDetector(
paths=device_paths, expected_count=len(device_paths)
)
def get_input_devices(self) -> DeviceDetector:
"""Get input device paths for testing."""
if "input" not in self._created_devices:
devices = [
self._create_device(
self.temp_path / "input" / "event0", 13, 64
),
self._create_device(
self.temp_path / "input" / "event1", 13, 65
),
self._create_device(self.temp_path / "input" / "mice", 13, 63),
]
self._created_devices["input"] = devices
self._set_mock_env_for_devices("input", devices)
device_paths = [str(d) for d in self._created_devices["input"]]
return DeviceDetector(
paths=device_paths, expected_count=len(device_paths)
)
def get_gpu_devices(self) -> DeviceDetector:
"""Get GPU device paths for testing."""
if "gpu" not in self._created_devices:
devices = [
self._create_device(
self.temp_path / "dri" / "renderD128", 226, 128
)
]
self._created_devices["gpu"] = devices
self._set_mock_env_for_devices("gpu", devices)
device_paths = [str(d) for d in self._created_devices["gpu"]]
return DeviceDetector(
paths=device_paths, expected_count=len(device_paths)
)
def get_dvb_devices(self) -> DeviceDetector:
"""Get DVB device paths for testing."""
if "dvb" not in self._created_devices:
devices = [
self._create_device(
self.temp_path / "dvb" / "adapter0" / "frontend0", 212, 4
),
self._create_device(
self.temp_path / "dvb" / "adapter0" / "demux0", 212, 5
),
]
self._created_devices["dvb"] = devices
self._set_mock_env_for_devices("dvb", devices)
device_paths = [str(d) for d in self._created_devices["dvb"]]
return DeviceDetector(
paths=device_paths, expected_count=len(device_paths)
)
def get_ttyusb_devices(self) -> DeviceDetector:
"""Get USB TTY device paths for testing."""
if "ttyUSB" not in self._created_devices:
devices = [
self._create_device(self.temp_path / "ttyUSB0", 188, 0),
self._create_device(self.temp_path / "ttyUSB1", 188, 1),
]
self._created_devices["ttyUSB"] = devices
self._set_mock_env_for_devices("ttyUSB", devices)
device_paths = [str(d) for d in self._created_devices["ttyUSB"]]
return DeviceDetector(
paths=device_paths, expected_count=len(device_paths)
)
def get_radio_devices(self) -> DeviceDetector:
"""Get radio device paths for testing."""
if "radio" not in self._created_devices:
devices = [
self._create_device(self.temp_path / "radio0", 81, 64),
self._create_device(self.temp_path / "radio1", 81, 65),
]
self._created_devices["radio"] = devices
self._set_mock_env_for_devices("radio", devices)
device_paths = [str(d) for d in self._created_devices["radio"]]
return DeviceDetector(
paths=device_paths, expected_count=len(device_paths)
)
def get_ttys_devices(self) -> DeviceDetector:
"""Get TTY device paths for testing."""
if "ttys" not in self._created_devices:
devices = [
self._create_device(self.temp_path / "tty0", 4, 0),
self._create_device(self.temp_path / "tty1", 4, 1),
self._create_device(self.temp_path / "tty2", 4, 2),
]
self._created_devices["ttys"] = devices
self._set_mock_env_for_devices("ttys", devices)
device_paths = [str(d) for d in self._created_devices["ttys"]]
return DeviceDetector(
paths=device_paths, expected_count=len(device_paths)
)

View File

@ -0,0 +1,24 @@
[pytest]
testpaths = .
python_files = test_*.py
python_classes = Test*
python_functions = test_*
addopts =
--strict-markers
--verbose
--tb=short
markers =
unit: Unit tests that do not require external dependencies
integration: Integration tests that may require system resources
performance: Performance tests with timing requirements
slow: Tests that take more than 1 second to run
hook_execution: Tests that actually execute OCI hooks
json_validation: Tests that validate JSON structure
filterwarnings =
ignore::DeprecationWarning
ignore::PendingDeprecationWarning
log_cli = true
log_cli_level = INFO
log_cli_format = %(asctime)s [%(levelname)8s] %(name)s: %(message)s
log_cli_date_format = %Y-%m-%d %H:%M:%S
junit_family = xunit2

View File

@ -0,0 +1,5 @@
# Basic testing framework
pytest>=7.0.0
# Test fixtures and utilities
jsonschema>=4.0.0

View File

@ -0,0 +1,443 @@
#!/usr/bin/env python3
"""Tests for OCI hook configuration files."""
import json
import re
from pathlib import Path
from collections import Counter
import pytest
from test_utils import HookConfigLoader
TEST_SPEC = {
"version": "1.0.0",
"process": {
"terminal": False,
"user": {"uid": 0, "gid": 0},
"args": ["echo", "test"],
"env": [
"PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
],
"cwd": "/",
"capabilities": {
"bounding": [
"CAP_AUDIT_WRITE",
"CAP_KILL",
"CAP_NET_BIND_SERVICE",
],
"effective": [
"CAP_AUDIT_WRITE",
"CAP_KILL",
"CAP_NET_BIND_SERVICE",
],
"inheritable": [
"CAP_AUDIT_WRITE",
"CAP_KILL",
"CAP_NET_BIND_SERVICE",
],
"permitted": [
"CAP_AUDIT_WRITE",
"CAP_KILL",
"CAP_NET_BIND_SERVICE",
],
"ambient": [
"CAP_AUDIT_WRITE",
"CAP_KILL",
"CAP_NET_BIND_SERVICE",
],
},
"rlimits": [{"type": "RLIMIT_NOFILE", "hard": 1024, "soft": 1024}],
"noNewPrivileges": True,
},
"root": {"path": "rootfs", "readonly": True},
"hostname": "testing",
"mounts": [
{"destination": "/proc", "type": "proc", "source": "proc"},
{
"destination": "/dev",
"type": "tmpfs",
"source": "tmpfs",
"options": ["nosuid", "strictatime", "mode=755", "size=65536k"],
},
],
"annotations": {},
"linux": {
"resources": {},
"namespaces": [
{"type": "pid"},
{"type": "network"},
{"type": "ipc"},
{"type": "uts"},
{"type": "mount"},
],
"maskedPaths": [
"/proc/acpi",
"/proc/asound",
"/proc/kcore",
"/proc/keys",
"/proc/latency_stats",
"/proc/timer_list",
"/proc/timer_stats",
"/proc/sched_debug",
"/sys/firmware",
],
"readonlyPaths": [
"/proc/bus",
"/proc/fs",
"/proc/irq",
"/proc/sys",
"/proc/sysrq-trigger",
],
},
}
class TestHookConfigurations:
"""Test class for validating OCI hook JSON configurations."""
@pytest.fixture(scope="class")
def hook_configs(self):
"""Load all hook configuration files."""
return HookConfigLoader.load_all_hook_configs()
@staticmethod
def _get_hook_names():
"""Get hook names for parametrized tests."""
return HookConfigLoader.get_hook_names()
@pytest.mark.unit
@pytest.mark.parametrize("hook_name", _get_hook_names())
def test_json_syntax_validity(self, hook_configs, hook_name):
"""Test that hook JSON file has valid syntax."""
hook_data = hook_configs[hook_name]
config_path = hook_data["path"]
# Re-read and parse to ensure JSON is valid
try:
with open(config_path, "r", encoding="utf-8") as f:
json.load(f)
except json.JSONDecodeError as e:
pytest.fail(f"Invalid JSON syntax in {config_path}: {e}")
@pytest.mark.unit
@pytest.mark.parametrize("hook_name", _get_hook_names())
@pytest.mark.parametrize(
"required_field", ["version", "hook", "when", "stages"]
)
def test_required_schema_fields(
self, hook_configs, hook_name, required_field
):
"""Test that hook config has required OCI hook schema fields."""
hook_data = hook_configs[hook_name]
config = hook_data["config"]
config_path = hook_data["path"]
assert (
required_field in config
), f"Missing required field '{required_field}' in {config_path}"
@pytest.mark.unit
@pytest.mark.parametrize("hook_name", _get_hook_names())
def test_hook_path_field(self, hook_configs, hook_name):
"""Test that hook config has required OCI hook schema field 'path'."""
hook_data = hook_configs[hook_name]
hook_config = hook_data["config"].get("hook", {})
config_path = hook_data["path"]
assert (
"path" in hook_config
), f"Missing required hook field 'path' in {config_path}"
@pytest.mark.unit
@pytest.mark.parametrize("hook_name", _get_hook_names())
def test_version_format(self, hook_configs, hook_name):
"""Test that version field follows semantic versioning."""
semver_pattern = re.compile(r"^\d+\.\d+\.\d+$")
hook_data = hook_configs[hook_name]
config = hook_data["config"]
config_path = hook_data["path"]
version = config.get("version")
assert version, f"Version field is empty in {config_path}"
assert semver_pattern.match(
version
), f"Invalid version format '{version}' in {config_path}"
@pytest.mark.unit
@pytest.mark.parametrize("hook_name", _get_hook_names())
def test_valid_stages(self, hook_configs, hook_name):
"""Test that stages contain only valid OCI hook stages."""
hook_data = hook_configs[hook_name]
config = hook_data["config"]
config_path = hook_data["path"]
valid_stages = ["prestart", "precreate", "poststart", "poststop"]
stages = config.get("stages", [])
assert isinstance(
stages, list
), f"Stages must be a list in {config_path}"
assert (
len(stages) > 0
), f"At least one stage must be specified in {config_path}"
assert all(
stage in valid_stages for stage in stages
), f"Invalid stages in {config_path}. Valid stages: {valid_stages}"
@pytest.mark.unit
@pytest.mark.parametrize("hook_name", _get_hook_names())
def test_annotation_patterns(self, hook_configs, hook_name):
"""Test that annotation patterns are valid regular expressions."""
hook_data = hook_configs[hook_name]
config = hook_data["config"]
config_path = hook_data["path"]
when_section = config.get("when", {})
annotations = when_section.get("annotations", {})
def is_valid_regex(pattern):
try:
re.compile(pattern)
return True
except re.error:
return False
invalid_patterns = {
p: "key" for p in annotations.keys() if not is_valid_regex(p)
}
invalid_value_patterns = {
v: "value"
for v in annotations.values()
if isinstance(v, str) and not is_valid_regex(v)
}
assert not invalid_patterns, (
f"Invalid regex in annotation keys: {invalid_patterns} "
f"in {config_path}"
)
assert not invalid_value_patterns, (
f"Invalid regex in annotation values: {invalid_value_patterns} "
f"in {config_path}"
)
@pytest.mark.integration
@pytest.mark.parametrize("hook_name", _get_hook_names())
def test_hook_executable_exists(self, hook_configs, hook_name):
"""Test that hook executables exist and are executable."""
hook_data = hook_configs[hook_name]
config_path = hook_data["path"]
hook_path = Path(hook_data["config"]["hook"]["path"])
# For tests, the hook might be in the source directory rather than
# installed location - try absolute path first, then relative
try:
# Check if absolute path works
hook_path.stat()
except OSError:
# If absolute path fails, try relative to config file
hook_path = config_path.parent / hook_path.name
assert hook_path.exists(), f"Hook executable not found: {hook_path}"
assert hook_path.is_file(), f"Hook executable not a file: {hook_path}"
@pytest.mark.unit
def test_device_manager_annotations(self, hook_configs):
"""Test that device manager config matches supported annotations."""
hook_name = "oci-qm-device-manager"
assert hook_name in hook_configs, f"Hook {hook_name} not found"
device_manager_config = hook_configs[hook_name]["config"]
annotations = device_manager_config.get("when", {}).get(
"annotations", {}
)
# Check that device patterns exist
device_patterns = [p for p in annotations.keys() if "device" in p]
assert (
device_patterns
), "Device manager should support device annotations"
# Check that wayland patterns exist
wayland_patterns = [p for p in annotations.keys() if "wayland" in p]
assert (
wayland_patterns
), "Device manager should support Wayland annotations"
# Test that device patterns match expected device types
test_annotations = [
"org.containers.qm.device.audio",
"org.containers.qm.device.video",
"org.containers.qm.device.input",
"org.containers.qm.device.ttys",
]
unmatched_patterns = [
p
for p in device_patterns
if not all(re.match(p, a) for a in test_annotations)
]
assert not unmatched_patterns, (
f"Device patterns {unmatched_patterns} failed to match all "
"expected annotations"
)
@pytest.mark.unit
def test_wayland_client_annotations(self, hook_configs):
"""Test that wayland client config matches supported annotations."""
hook_name = "oci-qm-wayland-client-devices"
assert hook_name in hook_configs, f"Hook {hook_name} not found"
wayland_config = hook_configs[hook_name]["config"]
annotations = wayland_config.get("when", {}).get("annotations", {})
# Check that wayland-client patterns exist
wayland_patterns = [
p for p in annotations.keys() if "wayland-client" in p
]
assert (
wayland_patterns
), "Wayland client should have wayland-client pattern"
# Test that patterns match expected annotations
test_annotations = ["org.containers.qm.wayland-client.gpu"]
unmatched_patterns = [
p
for p in wayland_patterns
if not all(re.match(p, a) for a in test_annotations)
]
assert not unmatched_patterns, (
f"Wayland patterns {unmatched_patterns} failed to match all "
"expected annotations"
)
@pytest.mark.unit
def test_no_duplicate_annotations(self, hook_configs):
"""Test that there are no overlapping annotation patterns."""
# Create a flat list of all annotation patterns from all hooks
all_patterns = [
pattern
for hook_data in hook_configs.values()
for pattern in hook_data["config"]
.get("when", {})
.get("annotations", {})
.keys()
]
# Count occurrences of each pattern
pattern_counts = Counter(all_patterns)
# Assert no duplicate patterns exist using named expression
assert not (
duplicates := {
pattern: count
for pattern, count in pattern_counts.items()
if count > 1
}
), "Duplicate annotation patterns found: {}".format( # pylint: disable=C0209 # noqa: E501
{
pattern: [
name
for name, data in hook_configs.items()
if pattern
in data["config"].get("when", {}).get("annotations", {})
]
for pattern in duplicates
}
)
@pytest.mark.unit
@pytest.mark.parametrize("hook_name", _get_hook_names())
def test_json_formatting(self, hook_configs, hook_name):
"""Test that JSON file is properly formatted."""
hook_data = hook_configs[hook_name]
config_path = hook_data["path"]
config = hook_data["config"]
# Read the original file content
with open(config_path, "r", encoding="utf-8") as f:
original_content = f.read()
# Generate formatted JSON
_ = json.dumps(config, indent=2, sort_keys=False) + "\n"
# Check if formatting is consistent (allowing for minor variations)
# This is a basic check - in practice you might want to be
# more lenient
assert (
len(original_content.strip()) > 0
), f"JSON file {config_path} appears to be empty"
# Check that it's valid JSON by trying to parse it
try:
json.loads(original_content)
except json.JSONDecodeError as e:
pytest.fail(f"Invalid JSON in {config_path}: {e}")
@pytest.mark.integration
@pytest.mark.parametrize("hook_name", _get_hook_names())
def test_hook_config_integration(self, hook_configs, hook_name):
"""Test that hook config integrates correctly with its executable."""
hook_data = hook_configs[hook_name]
config = hook_data["config"]
config_path = hook_data["path"]
# Get hook executable path
hook_path = config.get("hook", {}).get("path", "")
assert hook_path, f"Hook path not found in {config_path}"
# Try absolute path first, then relative to config directory
full_hook_path = Path(hook_path)
try:
# Check if absolute path works
full_hook_path.stat()
except OSError:
# If absolute path fails, try relative to config directory
full_hook_path = config_path.parent / Path(hook_path).name
# Check that executable exists
assert full_hook_path.exists(), (
f"Hook executable not found: {full_hook_path} "
f"(configured in {config_path})"
)
# Check that it's executable
assert (
full_hook_path.is_file()
), f"Hook path is not a file: {full_hook_path}"
# Basic executable check (if we can check permissions)
try:
assert (
full_hook_path.stat().st_mode & 0o111
), f"Hook file is not executable: {full_hook_path}"
except OSError:
# Skip permission check if we can't access file stats
pass
@pytest.mark.unit
@pytest.mark.parametrize("hook_name", _get_hook_names())
def test_stage_appropriateness(self, hook_configs, hook_name):
"""Test that hook uses appropriate stages for its functionality."""
hook_data = hook_configs[hook_name]
config = hook_data["config"]
stages = config.get("stages", [])
# Device management hooks should use precreate stage
# because they need to modify the OCI spec before container creation
assert "precreate" in stages, (
f"Hook {hook_name} should use 'precreate' stage for device "
"management"
)
# Should not use poststop for device hooks
assert (
"poststop" not in stages
), f"Device hook {hook_name} should not use 'poststop' stage"

View File

@ -0,0 +1,107 @@
#!/usr/bin/env python3
"""Basic functionality tests for QM device manager."""
import pytest
from conftest import DeviceCounter
class TestQMOCIHooksBasic:
"""Basic functionality tests for QM device manager."""
@pytest.mark.unit
@pytest.mark.parametrize(
"hook_name", ["qm_device_manager", "wayland_client_devices"]
)
@pytest.mark.parametrize(
"json_spec",
[
{"annotations": {}, "linux": {}},
{
"annotations": {"org.containers.qm.device.unknown": "true"},
"linux": {},
},
{
"annotations": {"org.containers.qm.device.audio": "false"},
"linux": {},
},
],
ids=["empty_spec", "unknown_spec", "invalid_spec"],
)
def test_basic_annotations(
self, hook_name, json_spec, hook_runner, oci_spec_validator
):
"""Test hook with basic annotations returns unchanged spec."""
result = hook_runner.run_hook(hook_name, json_spec)
assert result.success, f"Hook failed: {result.stderr}"
assert oci_spec_validator(result.output_spec), "Output spec is invalid"
assert (
DeviceCounter.count_devices(result.output_spec) == 0
), "No devices should be added"
@pytest.mark.unit
@pytest.mark.parametrize(
"invalid_spec",
[
# Missing required 'linux' property
{"annotations": {"com.example": "value"}},
# 'annotations' should be an object, not a string
{"annotations": "not-an-object", "linux": {}},
# Add a property not defined in the schema
{
"annotations": {"com.example": "value"},
"linux": {},
"extra": 123,
},
],
)
def test_invalid_annotations(self, oci_spec_validator, invalid_spec):
"""Test invalid annotations are rejected."""
assert not oci_spec_validator(
invalid_spec
), "Invalid spec should be rejected"
@pytest.mark.unit
def test_missing_linux_section(self, hook_runner):
"""Test hook creates linux section if missing."""
malformed_json = {
"annotations": {"org.containers.qm.device.audio": "true"}
# Missing linux section
}
result = hook_runner.run_hook("qm_device_manager", malformed_json)
assert result.success, f"Hook failed: {result.stderr}"
assert (
"linux" in result.output_spec
), "Hook should create linux section"
assert isinstance(
result.output_spec["linux"], dict
), "Linux section should be a dict"
@pytest.mark.unit
@pytest.mark.parametrize(
"json_spec",
[
# Non-wayland annotations ignored
{
"annotations": {"org.containers.qm.device.audio": "true"},
"linux": {},
},
# Unknown wayland annotations ignored
{
"annotations": {
"org.containers.qm.wayland-client.unknown": "true"
},
"linux": {},
},
],
ids=["non_wayland_ignored", "unknown_wayland_ignored"],
)
def test_wayland_annotations(self, hook_runner, json_spec, device_counter):
"""Test wayland annotations are processed correctly."""
result = hook_runner.run_hook("wayland_client_devices", json_spec)
assert result.success, f"Hook failed: {result.stderr}"
assert (
device_counter.count_devices(result.output_spec) == 0
), "No devices should be added"

View File

@ -0,0 +1,155 @@
#!/usr/bin/env python3
"""Device detection and annotation tests for QM device manager."""
import pytest
from conftest import DeviceCounter
class TestQMDeviceManagerDevices:
"""Device annotation tests for QM device manager."""
@pytest.mark.integration
@pytest.mark.hook_execution
def test_audio_device_annotation(
self, hook_runner, sample_specs, device_counter
):
"""Test audio device annotation executes successfully."""
result = hook_runner.run_hook(
"qm_device_manager", sample_specs["audio_device"]
)
assert result.success, f"Hook failed: {result.stderr}"
# Hook should succeed and produce valid output regardless of
# available devices (device-specific testing in temp_devices tests)
total_devices = device_counter.count_devices(result.output_spec)
assert total_devices >= 0, "Device count should be non-negative"
@pytest.mark.integration
@pytest.mark.hook_execution
def test_multiple_device_annotations(
self, hook_runner, sample_specs, device_counter
):
"""Test multiple device annotations."""
result = hook_runner.run_hook(
"qm_device_manager", sample_specs["multiple_devices"]
)
assert result.success, f"Hook failed: {result.stderr}"
# Should have devices for at least one of the requested types
# (depending on what's available in test environment)
total_devices = device_counter.count_devices(result.output_spec)
# Even if no devices are available, hook should succeed
assert total_devices >= 0, "Device count should be non-negative"
@pytest.mark.unit
@pytest.mark.parametrize(
"device_type,annotation_key",
[
("audio", "org.containers.qm.device.audio"),
("video", "org.containers.qm.device.video"),
("input", "org.containers.qm.device.input"),
("ttys", "org.containers.qm.device.ttys"),
("ttyUSB", "org.containers.qm.device.ttyUSB"),
("dvb", "org.containers.qm.device.dvb"),
("radio", "org.containers.qm.device.radio"),
],
)
def test_individual_device_types(
self, hook_runner, device_type, annotation_key
):
"""Test individual device type annotations."""
spec = {"annotations": {annotation_key: "true"}, "linux": {}}
result = hook_runner.run_hook("qm_device_manager", spec)
assert (
result.success
), f"Hook failed for {device_type}: {result.stderr}"
# Validate result.output_spec structure
assert "linux" in result.output_spec
assert ("devices" in result.output_spec.get("linux", {})) or (
DeviceCounter.count_devices(result.output_spec) == 0
)
@pytest.mark.unit
def test_audio_device_annotation_with_temp_devices(
self, hook_runner, sample_specs, device_counter, temp_devices
):
"""Test audio device annotation with specific device creation."""
device_detector = temp_devices.get_audio_devices()
result = hook_runner.run_hook(
"qm_device_manager",
sample_specs["audio_device"],
mock_devices=device_detector.mock_devices(device_type="audio"),
)
assert result.success, f"Hook failed: {result.stderr}"
# Verify expected number of devices
device_count = device_counter.count_devices(result.output_spec)
assert device_count == device_detector.expected_count, (
f"Expected {device_detector.expected_count} audio devices, "
f"got {device_count}"
)
# Verify the specific temporary devices are present
devices = result.output_spec.get("linux", {}).get("devices", [])
found_paths = [d["path"] for d in devices]
assert all(
temp_path in found_paths for temp_path in device_detector.paths
), (
f"All temporary audio devices should be found in output. "
f"Expected: {device_detector.paths}, Found: {found_paths}"
)
@pytest.mark.unit
@pytest.mark.parametrize(
"device_type,device_method",
[
("video", "get_video_devices"),
("input", "get_input_devices"),
("dvb", "get_dvb_devices"),
("ttyUSB", "get_ttyusb_devices"),
("radio", "get_radio_devices"),
("ttys", "get_ttys_devices"),
],
)
# pylint: disable=too-many-positional-arguments
def test_device_annotation_with_temp_devices(
self,
hook_runner,
device_counter,
temp_devices,
device_type,
device_method,
):
"""Test various device types with specific device creation."""
device_detector = getattr(temp_devices, device_method)()
annotation_key = f"org.containers.qm.device.{device_type}"
spec = {
"annotations": {annotation_key: "true"},
"linux": {},
}
result = hook_runner.run_hook(
"qm_device_manager",
spec,
mock_devices=device_detector.mock_devices(device_type),
)
assert (
result.success
), f"Hook failed for {device_type}: {result.stderr}"
device_count = device_counter.count_devices(result.output_spec)
assert device_count == device_detector.expected_count, (
f"Expected {device_detector.expected_count} {device_type} "
f"devices, got {device_count}"
)

View File

@ -0,0 +1,134 @@
#!/usr/bin/env python3
"""Error handling and edge case tests for QM device manager."""
import pytest
class TestQMDeviceManagerErrorHandling:
"""Error handling and edge case tests."""
@pytest.mark.unit
@pytest.mark.hook_execution
def test_non_qm_annotations_ignored(self, hook_runner, device_counter):
"""Test that non-QM annotations are ignored."""
spec = {
"annotations": {
"org.opencontainers.image.title": "test",
"com.example.custom": "value",
},
"linux": {},
}
result = hook_runner.run_hook("qm_device_manager", spec)
assert result.success, f"Hook failed: {result.stderr}"
assert (
device_counter.count_devices(result.output_spec) == 0
), "No devices should be added for non-QM annotations"
@pytest.mark.unit
def test_hook_with_existing_devices(self, hook_runner):
"""Test hook behavior when devices already exist."""
spec_with_devices = {
"annotations": {"org.containers.qm.device.audio": "true"},
"linux": {
"devices": [
{
"path": "/dev/existing",
"type": "c",
"major": 1,
"minor": 3,
}
]
},
}
result = hook_runner.run_hook("qm_device_manager", spec_with_devices)
assert result.success, f"Hook failed: {result.stderr}"
# Should preserve existing devices and potentially add new ones
devices = result.output_spec.get("linux", {}).get("devices", [])
existing_paths = [d["path"] for d in devices]
assert (
"/dev/existing" in existing_paths
), "Existing device should be preserved"
@pytest.mark.unit
def test_hook_with_existing_resources(self, hook_runner):
"""Test hook behavior when resources already exist."""
spec_with_resources = {
"annotations": {"org.containers.qm.wayland.seat": "true"},
"linux": {
"resources": {"devices": [{"allow": False, "type": "a"}]}
},
}
result = hook_runner.run_hook("qm_device_manager", spec_with_resources)
assert result.success, f"Hook failed: {result.stderr}"
# Should preserve existing resources
resources = result.output_spec.get("linux", {}).get("resources", {})
devices_limit = resources.get("devices", [])
# Check that the existing rule is preserved
deny_all_rule = {"allow": False, "type": "a"}
assert (
deny_all_rule in devices_limit
), "Existing resource rules should be preserved"
class TestWaylandClientDevicesErrorHandling:
"""Error handling tests for Wayland client devices."""
@pytest.mark.unit
def test_annotation_isolation(self, hook_runner, device_counter):
"""Test that invalid annotations don't affect valid ones."""
spec = {
"annotations": {
"org.containers.qm.wayland-client.gpu": "true",
"org.containers.qm.wayland-client.invalid": "bad_value",
"org.opencontainers.image.title": "test",
},
"linux": {},
}
result = hook_runner.run_hook("wayland_client_devices", spec)
assert result.success, f"Hook failed: {result.stderr}"
# Valid GPU annotation should still be processed
total_devices = device_counter.count_devices(result.output_spec)
assert total_devices >= 0, "Valid annotations should be processed"
@pytest.mark.unit
def test_empty_annotation_value(self, hook_runner, device_counter):
"""Test handling of empty annotation values."""
spec = {
"annotations": {"org.containers.qm.wayland-client.gpu": ""},
"linux": {},
}
result = hook_runner.run_hook("wayland_client_devices", spec)
assert result.success, f"Hook failed: {result.stderr}"
# Empty value should be treated as falsy
total_devices = device_counter.count_devices(result.output_spec)
assert (
total_devices == 0
), "Empty annotation value should not add devices"
@pytest.mark.unit
def test_unknown_annotation_values(self, hook_runner, device_counter):
"""Test handling of unknown annotation values."""
spec = {
"annotations": {"org.containers.qm.wayland-client.gpu": "maybe"},
"linux": {},
}
result = hook_runner.run_hook("wayland_client_devices", spec)
assert result.success, f"Hook failed: {result.stderr}"
# Unknown values should typically be treated as falsy for safety
total_devices = device_counter.count_devices(result.output_spec)
assert (
total_devices == 0
), "Unknown annotation values should not add devices"

View File

@ -0,0 +1,65 @@
#!/usr/bin/env python3
"""Logging tests for QM device manager and Wayland client devices."""
import pytest
class TestQMDeviceManagerLogging:
"""Logging functionality tests."""
@pytest.mark.unit
@pytest.mark.hook_execution
def test_log_file_creation(self, hook_runner, log_checker):
"""Test that hook creates log file."""
empty_spec = {"annotations": {}, "linux": {}}
result = hook_runner.run_hook("qm_device_manager", empty_spec)
assert result.success, f"Hook failed: {result.stderr}"
assert log_checker("qm-device-manager"), "Log should contain hook name"
@pytest.mark.unit
@pytest.mark.hook_execution
def test_log_content_validation(
self, hook_runner, sample_specs, log_checker
):
"""Test that hook logs contain expected content."""
result = hook_runner.run_hook(
"qm_device_manager", sample_specs["audio_device"]
)
assert result.success, f"Hook failed: {result.stderr}"
assert log_checker(
"QM Device Manager"
), "Log should contain hook description"
assert log_checker("completed successfully")
class TestWaylandClientDevicesLogging:
"""Logging functionality tests."""
@pytest.mark.unit
@pytest.mark.hook_execution
def test_log_file_creation(self, hook_runner, log_checker):
"""Test that hook creates log file."""
empty_spec = {"annotations": {}, "linux": {}}
result = hook_runner.run_hook("wayland_client_devices", empty_spec)
assert result.success, f"Hook failed: {result.stderr}"
assert log_checker(
"qm-wayland-client-devices"
), "Log should contain hook name"
@pytest.mark.unit
@pytest.mark.hook_execution
def test_log_content_validation(
self, hook_runner, sample_specs, log_checker
):
"""Test that hook logs contain expected content."""
result = hook_runner.run_hook(
"wayland_client_devices", sample_specs["wayland_gpu"]
)
assert result.success, f"Hook failed: {result.stderr}"
assert log_checker(
"qm-wayland-client-devices"
), "Log should contain hook name"

View File

@ -0,0 +1,89 @@
#!/usr/bin/env python3
"""Performance tests for QM device manager and Wayland client devices."""
import time
import pytest
class TestQMDeviceManagerPerformance:
"""Performance and timing tests."""
@pytest.mark.performance
def test_hook_performance(self, hook_runner, sample_specs):
"""Test that hook executes within reasonable time."""
start_time = time.time()
result = hook_runner.run_hook(
"qm_device_manager", sample_specs["multiple_devices"]
)
end_time = time.time()
assert result.success, f"Hook failed: {result.stderr}"
execution_time = end_time - start_time
# Hook should complete within 5 seconds (generous limit)
assert (
execution_time < 5.0
), f"Hook took too long: {execution_time:.2f}s"
@pytest.mark.performance
@pytest.mark.parametrize("iteration", range(5))
def test_multiple_executions_performance(
self, hook_runner, sample_specs, iteration
):
"""Test consistent performance across multiple executions."""
start_time = time.time()
result = hook_runner.run_hook(
"qm_device_manager", sample_specs["audio_device"]
)
end_time = time.time()
assert (
result.success
), f"Hook failed on iteration {iteration}: {result.stderr}"
execution_time = end_time - start_time
assert (
execution_time < 3.0
), f"Execution {iteration} too slow: {execution_time:.2f}s"
class TestWaylandClientDevicesPerformance:
"""Performance tests for Wayland client devices."""
@pytest.mark.performance
def test_hook_performance(self, hook_runner, sample_specs):
"""Test Wayland client devices hook performance."""
start_time = time.time()
result = hook_runner.run_hook(
"wayland_client_devices", sample_specs["wayland_gpu"]
)
end_time = time.time()
assert result.success, f"Hook failed: {result.stderr}"
execution_time = end_time - start_time
assert (
execution_time < 3.0
), f"Hook took too long: {execution_time:.2f}s"
@pytest.mark.performance
@pytest.mark.parametrize("iteration", range(3))
def test_multiple_executions_performance(
self, hook_runner, sample_specs, iteration
):
"""Test consistent performance across multiple executions."""
start_time = time.time()
result = hook_runner.run_hook(
"wayland_client_devices", sample_specs["wayland_gpu"]
)
end_time = time.time()
assert (
result.success
), f"Hook failed on iteration {iteration}: {result.stderr}"
execution_time = end_time - start_time
assert (
execution_time < 2.0
), f"Execution {iteration} too slow: {execution_time:.2f}s"

View File

@ -0,0 +1,129 @@
#!/usr/bin/env python3
"""Validation tests for QM device manager."""
import pytest
class TestQMDeviceManagerValidation:
"""JSON and structure validation tests."""
@pytest.mark.unit
def test_output_json_structure(
self, hook_runner, sample_specs, oci_spec_validator
):
"""Test that hook output follows OCI specification structure."""
result = hook_runner.run_hook(
"qm_device_manager", sample_specs["audio_device"]
)
assert result.success, f"Hook failed: {result.stderr}"
assert oci_spec_validator(result.output_spec), "Output spec is invalid"
@pytest.mark.unit
def test_device_structure_validation(self, hook_runner, sample_specs):
"""Test that device entries have correct structure."""
result = hook_runner.run_hook(
"qm_device_manager", sample_specs["multiple_devices"]
)
assert result.success, f"Hook failed: {result.stderr}"
devices = result.output_spec.get("linux", {}).get("devices", [])
# Check that all devices have required fields
required_fields = ["path", "type", "major", "minor"]
assert all(
field in device for device in devices for field in required_fields
), "All devices must have required fields: path, type, major, minor"
# Check path types
assert all(
isinstance(d["path"], str) for d in devices
), "Path must be str"
# Check type values
assert all(
d["type"] in ["c", "b"] for d in devices
), "Type must be c or b"
# Check major/minor are integers
assert all(
isinstance(d["major"], int) for d in devices
), "Major must be int"
assert all(
isinstance(d["minor"], int) for d in devices
), "Minor must be int"
@pytest.mark.unit
def test_resource_structure_validation(self, hook_runner):
"""Test that resource entries have correct structure."""
spec = {
"annotations": {"org.containers.qm.wayland.seat": "true"},
"linux": {},
}
result = hook_runner.run_hook("qm_device_manager", spec)
assert result.success, f"Hook failed: {result.stderr}"
# Check devices limit structure
devices_limit = (
result.output_spec.get("linux", {})
.get("resources", {})
.get("devices", [])
)
# Validate all device rules have required fields
assert all(
"allow" in device_rule for device_rule in devices_limit
), "All device rules must have 'allow' field"
assert all(
"type" in device_rule for device_rule in devices_limit
), "All device rules must have 'type' field"
assert all(
isinstance(device_rule["allow"], bool)
for device_rule in devices_limit
), "All 'allow' fields must be bool"
assert all(
device_rule["type"] in ["c", "b", "a"]
for device_rule in devices_limit
), "All device types must be 'c', 'b', or 'a'"
@pytest.mark.unit
def test_empty_annotations_validation(
self, hook_runner, oci_spec_validator
):
"""Test validation with empty annotations."""
empty_spec = {"annotations": {}, "linux": {}}
result = hook_runner.run_hook("qm_device_manager", empty_spec)
assert result.success, f"Hook failed: {result.stderr}"
assert oci_spec_validator(result.output_spec), "Output should be valid"
@pytest.mark.unit
@pytest.mark.parametrize(
"malformed_spec",
[
# Non-string annotation values should be handled gracefully
{
"annotations": {"org.containers.qm.device.audio": True},
"linux": {},
},
{
"annotations": {"org.containers.qm.device.audio": 123},
"linux": {},
},
{
"annotations": {"org.containers.qm.device.audio": []},
"linux": {},
},
],
ids=["boolean_value", "integer_value", "list_value"],
)
def test_malformed_annotation_values(self, hook_runner, malformed_spec):
"""Test handling of malformed annotation values."""
result = hook_runner.run_hook("qm_device_manager", malformed_spec)
# Hook should not crash, but may not process the annotation
assert (
result.success
), f"Hook should handle malformed values: {result.stderr}"

View File

@ -0,0 +1,97 @@
#!/usr/bin/env python3
"""Wayland seat functionality tests for QM device manager."""
import pytest
class TestQMDeviceManagerWayland:
"""Wayland seat annotation tests."""
@pytest.mark.unit
@pytest.mark.parametrize(
"seat_annotation",
[
"org.containers.qm.wayland.seat",
"org.containers.qm.wayland.seat.0",
"org.containers.qm.wayland.seat.1",
],
)
def test_wayland_seat_annotation(
self, hook_runner, seat_annotation, device_counter
):
"""Test Wayland seat annotations."""
spec = {
"annotations": {seat_annotation: "true"},
"linux": {},
}
result = hook_runner.run_hook("qm_device_manager", spec)
assert result.success, f"Hook failed: {result.stderr}"
# Verify devices and resources are added for seat
device_count = device_counter.count_devices(result.output_spec)
resource_count = device_counter.count_resources(result.output_spec)
assert device_count >= 0, "Device count should be non-negative"
assert resource_count >= 0, "Resource count should be non-negative"
@pytest.mark.unit
def test_wayland_seat_with_existing_devices(self, hook_runner):
"""Test wayland seat annotation with existing devices."""
spec_with_devices = {
"annotations": {"org.containers.qm.wayland.seat": "true"},
"linux": {
"devices": [
{
"path": "/dev/existing",
"type": "c",
"major": 1,
"minor": 3,
}
]
},
}
result = hook_runner.run_hook("qm_device_manager", spec_with_devices)
assert result.success, f"Hook failed: {result.stderr}"
# Should preserve existing devices
devices = result.output_spec.get("linux", {}).get("devices", [])
existing_paths = [d["path"] for d in devices]
assert (
"/dev/existing" in existing_paths
), "Existing device should be preserved"
@pytest.mark.unit
@pytest.mark.parametrize(
"spec",
[
{
"annotations": {
"org.containers.qm.wayland.seat.0": "true",
"org.containers.qm.wayland.seat.1": "true",
},
"linux": {},
},
{
"annotations": {
"org.containers.qm.wayland.seat": "seat0",
"org.containers.qm.wayland.seat.0": "true",
"org.containers.qm.wayland.seat.1": "true",
},
"linux": {},
},
],
ids=["multiple_seats", "conflicting_seats"],
)
def test_multiple_wayland_seats(self, hook_runner, device_counter, spec):
"""Test multiple Wayland seat annotations."""
result = hook_runner.run_hook("qm_device_manager", spec)
assert result.success, f"Hook failed: {result.stderr}"
# Should process both seats
device_count = device_counter.count_devices(result.output_spec)
resource_count = device_counter.count_resources(result.output_spec)
assert device_count >= 0, "Should handle multiple seats"
assert resource_count >= 0, "Resource count should be non-negative"

View File

@ -0,0 +1,238 @@
"""Shared test utilities for OCI hooks testing."""
import json
import subprocess
import time
from pathlib import Path
from dataclasses import dataclass
from typing import Dict, Any, Optional
import jsonschema
@dataclass
class HookResult:
"""Result of running an OCI hook."""
success: bool
output_spec: Dict[str, Any]
stdout: str
stderr: str
execution_time: float
class HookRunner:
"""Class for running OCI hooks in test environment."""
def __init__(self, test_env: Dict[str, str]):
"""Initialize with test environment variables."""
self.test_env = test_env
def run_hook(
self,
hook_name: str,
input_spec: Dict[str, Any],
mock_devices: Optional[Dict[str, str]] = None,
) -> HookResult:
"""Run a hook with given input spec and return result."""
hook_paths = {
"qm_device_manager": "../qm-device-manager/oci-qm-device-manager",
"wayland_client_devices": (
"../wayland-client-devices/oci-qm-wayland-client-devices"
),
}
if hook_name not in hook_paths:
raise ValueError(f"Unknown hook: {hook_name}")
hook_path = hook_paths[hook_name]
input_json = json.dumps(input_spec)
# Use provided test environment (including TEST_LOGFILE)
env = self.test_env.copy()
# Add mock device environment variables if provided
if mock_devices:
for device_type, device_list in mock_devices.items():
env_var = f"TEST_MOCK_{device_type.upper()}_DEVICES"
env[env_var] = device_list
start_time = time.time()
result = subprocess.run(
[hook_path],
input=input_json,
text=True,
capture_output=True,
env=env,
cwd=Path(__file__).parent,
check=False,
)
execution_time = time.time() - start_time
# Parse output JSON if hook succeeded
output_spec = {}
if result.returncode == 0 and result.stdout.strip():
try:
output_spec = json.loads(result.stdout)
except json.JSONDecodeError:
# If output is not valid JSON, treat as failure
pass
return HookResult(
success=result.returncode == 0,
output_spec=output_spec,
stdout=result.stdout,
stderr=result.stderr,
execution_time=execution_time,
)
class HookConfigLoader:
"""Utility for loading and managing hook configurations."""
@staticmethod
def load_all_hook_configs() -> Dict[str, Dict[str, Any]]:
"""Load all hook configuration files."""
hook_dir = Path(__file__).parent.parent
def _load_config(json_file):
with open(json_file, "r", encoding="utf-8") as f:
return json.load(f)
return {
json_file.stem: {
"path": json_file,
"config": _load_config(json_file),
}
for json_file in hook_dir.rglob("*.json")
if "oci-qm-" in json_file.name
}
@staticmethod
def get_hook_names() -> list:
"""Get list of all hook names."""
return list(HookConfigLoader.load_all_hook_configs().keys())
class OciSpecValidator:
"""JSON schema validator for OCI specifications."""
# Simplified OCI spec schema for validation
OCI_SCHEMA = {
"type": "object",
"properties": {
"annotations": {
"type": "object",
"additionalProperties": {"type": "string"},
},
"linux": {
"type": "object",
"properties": {
"devices": {
"type": "array",
"items": {
"type": "object",
"properties": {
"path": {"type": "string"},
"type": {"type": "string"},
"major": {"type": "integer"},
"minor": {"type": "integer"},
"fileMode": {"type": "integer"},
"uid": {"type": "integer"},
"gid": {"type": "integer"},
},
"required": ["path", "type", "major", "minor"],
},
},
"resources": {
"type": "object",
"properties": {
"devices": {
"type": "array",
"items": {
"type": "object",
"properties": {
"allow": {"type": "boolean"},
"type": {"type": "string"},
"major": {"type": "integer"},
"minor": {"type": "integer"},
"access": {"type": "string"},
},
"required": [
"allow",
"type",
"major",
"minor",
"access",
],
},
}
},
},
},
"additionalProperties": False,
},
},
"required": ["annotations", "linux"],
"additionalProperties": False,
}
@classmethod
def validate(cls, spec: Dict[str, Any]) -> bool:
"""Validate an OCI spec against the schema."""
try:
jsonschema.validate(spec, cls.OCI_SCHEMA)
return True
except jsonschema.ValidationError:
return False
class LogChecker:
"""Utility for checking hook log files."""
def __init__(self, log_file_path: str):
"""Initialize with log file path."""
self.log_file_path = Path(log_file_path)
def __call__(self, pattern: str, should_exist: bool = True) -> bool:
"""
Check if pattern exists in hook log file (backward compatibility).
Args:
pattern: String pattern to search for
should_exist: Whether pattern should exist (True) or not (False)
Returns:
True if check passes, False otherwise
"""
if not self.log_exists():
return not should_exist
try:
content = self.log_file_path.read_text(encoding="utf-8")
pattern_found = pattern in content
return pattern_found if should_exist else not pattern_found
except OSError:
return False
def log_exists(self) -> bool:
"""Check if log file exists."""
return self.log_file_path.exists()
def log_contains(self, text: str) -> bool:
"""Check if log contains specific text."""
if not self.log_exists():
return False
content = self.log_file_path.read_text(encoding="utf-8")
return text in content
def get_log_lines(self) -> list:
"""Get all log lines as a list."""
try:
return (
self.log_file_path.read_text(encoding="utf-8")
.strip()
.split("\n")
)
except OSError:
return []

View File

@ -0,0 +1,178 @@
#!/usr/bin/env python3
"""Wayland GPU device tests."""
import pytest
class TestWaylandClientDevicesGPU:
"""GPU device detection tests for Wayland client containers."""
@pytest.mark.unit
def test_gpu_annotation_enabled(self, hook_runner, sample_specs):
"""Test GPU annotation processes correctly."""
result = hook_runner.run_hook(
"wayland_client_devices", sample_specs["wayland_gpu"]
)
assert result.success, f"Hook failed: {result.stderr}"
@pytest.mark.unit
@pytest.mark.parametrize("gpu_value", ["true", "1", "yes", "True", "YES"])
def test_gpu_annotation_valid_values(
self, hook_runner, device_counter, gpu_value
):
"""Test GPU annotation with various valid truthy values."""
spec = {
"annotations": {"org.containers.qm.wayland-client.gpu": gpu_value},
"linux": {},
}
result = hook_runner.run_hook("wayland_client_devices", spec)
assert (
result.success
), f"Hook failed with value '{gpu_value}': {result.stderr}"
# For truthy values, devices should be processed
total_devices = device_counter.count_devices(result.output_spec)
assert (
total_devices >= 0
), f"Truthy value '{gpu_value}' should enable GPU processing"
@pytest.mark.unit
@pytest.mark.parametrize("gpu_value", ["false", "0", "no", "False", "NO"])
def test_gpu_annotation_invalid_values(
self, hook_runner, device_counter, gpu_value
):
"""Test GPU annotation with various falsy values."""
spec = {
"annotations": {"org.containers.qm.wayland-client.gpu": gpu_value},
"linux": {},
}
result = hook_runner.run_hook("wayland_client_devices", spec)
assert (
result.success
), f"Hook failed with falsy value '{gpu_value}': {result.stderr}"
# For falsy values, no devices should be added
total_devices = device_counter.count_devices(result.output_spec)
assert (
total_devices == 0
), f"Falsy value '{gpu_value}' should not add GPU devices"
@pytest.mark.unit
@pytest.mark.parametrize(
"gpu_value", ["TrUe", "YeS", "tRuE", "yEs", "TRUE"]
)
def test_gpu_annotation_case_insensitive_truthy_values(
self, hook_runner, device_counter, gpu_value
):
"""Test GPU annotation with mixed-case truthy values."""
spec = {
"annotations": {"org.containers.qm.wayland-client.gpu": gpu_value},
"linux": {},
}
result = hook_runner.run_hook("wayland_client_devices", spec)
assert (
result.success
), f"Hook failed with mixed-case value '{gpu_value}': {result.stderr}"
total_devices = device_counter.count_devices(result.output_spec)
assert total_devices >= 0, (
f"Mixed-case truthy value '{gpu_value}' should enable GPU "
"processing"
)
@pytest.mark.unit
@pytest.mark.parametrize(
"gpu_value", ["FaLsE", "nO", "fAlSe", "No", "FALSE"]
)
def test_gpu_annotation_case_insensitive_falsy_values(
self, hook_runner, device_counter, gpu_value
):
"""Test GPU annotation with mixed-case falsy values."""
spec = {
"annotations": {"org.containers.qm.wayland-client.gpu": gpu_value},
"linux": {},
}
result = hook_runner.run_hook("wayland_client_devices", spec)
assert (
result.success
), f"Hook failed with mixed-case value '{gpu_value}': {result.stderr}"
# For falsy values, no devices should be added
total_devices = device_counter.count_devices(result.output_spec)
assert (
total_devices == 0
), f"Mixed-case falsy value '{gpu_value}' should not add GPU devices"
@pytest.mark.unit
@pytest.mark.parametrize(
"gpu_value",
[
"2", # Number other than 1
"42", # Random number
"maybe", # Unrelated string
"truthy", # Similar but not exact
"YES_PLEASE", # Contains valid word but extra chars
"null", # Null-like value
"", # Empty string
"[]", # JSON array string
"{}", # JSON object string
"true false", # Multiple values
"TRUE;true", # Semicolon separated
"on", # Common boolean-like value
"off", # Common boolean-like value
"enable", # Enable-like value
"disable", # Disable-like value
],
)
def test_gpu_annotation_malformed_values(
self, hook_runner, device_counter, gpu_value
):
"""Test GPU annotation with malformed or unexpected values."""
spec = {
"annotations": {"org.containers.qm.wayland-client.gpu": gpu_value},
"linux": {},
}
result = hook_runner.run_hook("wayland_client_devices", spec)
# Hook should handle malformed values gracefully without failing
assert result.success, (
f"Hook should not fail with malformed value '{gpu_value}': "
f"{result.stderr}"
)
# Malformed values should be treated as falsy (no GPU devices added)
total_devices = device_counter.count_devices(result.output_spec)
assert (
total_devices == 0
), f"Malformed value '{gpu_value}' should not enable GPU processing"
class TestWaylandClientDevicesGPUDevices:
"""GPU device tests for Wayland client containers."""
@pytest.mark.unit
def test_gpu_annotation(
self, hook_runner, sample_specs, device_counter, temp_devices
):
"""Test GPU annotation with temp devices."""
device_detector = temp_devices.get_gpu_devices()
result = hook_runner.run_hook(
"wayland_client_devices",
sample_specs["wayland_gpu"],
mock_devices=device_detector.mock_devices("gpu"),
)
assert result.success, f"Hook failed: {result.stderr}"
device_count = device_counter.count_devices(result.output_spec)
assert device_count == device_detector.expected_count, (
f"Expected {device_detector.expected_count} GPU devices, "
f"got {device_count}"
)
devices = result.output_spec.get("linux", {}).get("devices", [])
found_paths = [d["path"] for d in devices]
assert all(
temp_path in found_paths for temp_path in device_detector.paths
), "Temporary GPU device not found in output"

82
oci-hooks/tox.ini Normal file
View File

@ -0,0 +1,82 @@
[tox]
envlist = unit
skipsdist = true
[testenv:unit]
deps = -r tests/requirements.txt
allowlist_externals = chmod
passenv = FORCE_MOCK_DEVICES
changedir = tests
commands_pre =
chmod +x {toxinidir}/qm-device-manager/oci-qm-device-manager
chmod +x {toxinidir}/wayland-client-devices/oci-qm-wayland-client-devices
commands =
pytest -m unit --tb=short -v {posargs}
[testenv:integration]
deps = -r tests/requirements.txt
allowlist_externals = chmod
passenv = FORCE_MOCK_DEVICES
changedir = tests
commands_pre =
chmod +x {toxinidir}/qm-device-manager/oci-qm-device-manager
chmod +x {toxinidir}/wayland-client-devices/oci-qm-wayland-client-devices
commands =
pytest -m integration --tb=short -v {posargs}
[testenv:performance]
deps = -r tests/requirements.txt
allowlist_externals = chmod
passenv = FORCE_MOCK_DEVICES
changedir = tests
commands_pre =
chmod +x {toxinidir}/qm-device-manager/oci-qm-device-manager
chmod +x {toxinidir}/wayland-client-devices/oci-qm-wayland-client-devices
commands =
pytest -m performance --tb=short -v {posargs}
[testenv:all]
deps = -r tests/requirements.txt
allowlist_externals = chmod
passenv = FORCE_MOCK_DEVICES
changedir = tests
commands_pre =
chmod +x {toxinidir}/qm-device-manager/oci-qm-device-manager
chmod +x {toxinidir}/wayland-client-devices/oci-qm-wayland-client-devices
commands =
pytest --tb=short -v {posargs}
[testenv:lint]
deps =
black
pylint
shellcheck-py
allowlist_externals = shfmt
commands =
black --check --diff --line-length 79 tests/
pylint --rcfile=tests/.pylintrc tests/*.py
shellcheck qm-device-manager/oci-qm-device-manager
shellcheck wayland-client-devices/oci-qm-wayland-client-devices
shellcheck lib/common.sh
shellcheck lib/device-support.sh
shellcheck lib/mock-device-support.sh
shfmt -d -i 4 qm-device-manager/oci-qm-device-manager
shfmt -d -i 4 wayland-client-devices/oci-qm-wayland-client-devices
shfmt -d -i 4 lib/common.sh
shfmt -d -i 4 lib/device-support.sh
shfmt -d -i 4 lib/mock-device-support.sh
[testenv:format]
deps = black
allowlist_externals = shfmt
commands =
black --line-length 79 tests/
shfmt -w -i 4 qm-device-manager/oci-qm-device-manager
shfmt -w -i 4 wayland-client-devices/oci-qm-wayland-client-devices
shfmt -w -i 4 lib/common.sh
shfmt -w -i 4 lib/device-support.sh
shfmt -w -i 4 lib/mock-device-support.sh
[flake8]
max-line-length = 79
extend-ignore = E203, W503

View File

@ -0,0 +1,63 @@
# Wayland-client-devices
The wayland-client-devices OCI hook enables containers to access GPU hardware acceleration devices for Wayland client
applications that would run as qm's nested containers.
## Key Functionality
1. **GPU Device Discovery**: The hook automatically discovers and configures access to GPU render devices when
GPU support is enabled, including:
- GPU hardware acceleration devices
2. **Container Configuration**: It dynamically modifies the container's OCI configuration to include the necessary
GPU device permissions and access controls for Wayland client applications that require hardware acceleration.
3. **Comprehensive Logging**: All operations are logged to `/var/log/qm-wayland-client-devices.log` for monitoring and debugging.
## Configuration
The hook supports the following container annotation:
- `org.containers.qm.wayland-client.gpu`: Enables GPU device access for Wayland clients. When this annotation is
present, the hook will automatically detect and configure access to available render devices in `/dev/dri/`.
## Logging
The hook provides detailed logging of all operations:
- **Log File**: `/var/log/qm-wayland-client-devices.log`
- **Log Format**: `YYYY-MM-DD HH:MM:SS - qm-wayland-client-devices - LEVEL - MESSAGE`
- **Log Levels**: INFO, WARNING, ERROR
### Example Log Output
```text
2024-01-15 10:32:15 - qm-wayland-client-devices - INFO - Processing Wayland client GPU annotation: true
2024-01-15 10:32:15 - qm-wayland-client-devices - INFO - Scanning for GPU render devices
2024-01-15 10:32:15 - qm-wayland-client-devices - INFO - Adding GPU render device: /dev/dri/renderD128
2024-01-15 10:32:15 - qm-wayland-client-devices - INFO - Found 1 GPU render devices
2024-01-15 10:32:15 - qm-wayland-client-devices - INFO - Processing 1 GPU devices for Wayland client
2024-01-15 10:32:15 - qm-wayland-client-devices - INFO - Added GPU device: /dev/dri/renderD128
2024-01-15 10:32:15 - qm-wayland-client-devices - INFO - Successfully processed all GPU devices for Wayland client
2024-01-15 10:32:15 - qm-wayland-client-devices - INFO - Total devices in final spec: 1
2024-01-15 10:32:15 - qm-wayland-client-devices - INFO - QM Wayland Client Devices hook completed successfully
```
## Example Configuration
To use the Wayland-client-devices hook, you can create a dropin configuration file to add the necessary annotation
to your container:
1. Create a dropin directory and file:
```bash
mkdir -p /etc/containers/systemd/myapp.container.d/
```
2. Create a dropin file (e.g., `wayland-client.conf`):
```ini
[Container]
Annotation=org.containers.qm.wayland-client.gpu=true
```

View File

@ -0,0 +1,123 @@
#!/bin/bash
set -euo pipefail
# Source common utilities and appropriate device support library
SCRIPT_DIR="$(dirname "${BASH_SOURCE[0]}")"
# shellcheck source=../lib/common.sh disable=SC1091
source "${SCRIPT_DIR}/../lib/common.sh"
if [[ -n "${TEST_LOGFILE:-}" ]]; then
# Test mode - use mock device support
# shellcheck source=../lib/mock-device-support.sh disable=SC1091
source "${SCRIPT_DIR}/../lib/mock-device-support.sh"
else
# Normal mode - use standard device support
# shellcheck source=../lib/device-support.sh disable=SC1091
source "${SCRIPT_DIR}/../lib/device-support.sh"
fi
# Configuration
LOGFILE="${TEST_LOGFILE:-/var/log/qm-wayland-client-devices.log}"
# shellcheck disable=SC2034 # Used by log() function in device-support.sh
HOOK_NAME="qm-wayland-client-devices"
input="-"
CONTAINER_CONFIG=$(cat "$input")
if [[ -z "$CONTAINER_CONFIG" ]]; then
log "ERROR" "Failed to read OCI spec from stdin"
exit 1
fi
GPU_ENABLED=$(echo "$CONTAINER_CONFIG" | jq -r '.annotations["org.containers.qm.wayland-client.gpu"] // empty')
DEVNAME_LIST=()
if [[ "$GPU_ENABLED" =~ ^(true|1|yes|True|TRUE|YES)$ ]]; then
log "INFO" "Processing Wayland client GPU annotation: $GPU_ENABLED (enabled)"
# Find all the render devices available
RENDER_DEVICES=$(discover_gpu_devices)
log "INFO" "Scanning for GPU render devices"
for RENDER_DEVICE in $RENDER_DEVICES; do
DEVNAME_LIST+=("$RENDER_DEVICE")
log "INFO" "Adding GPU render device: $RENDER_DEVICE"
done
log "INFO" "Found ${#DEVNAME_LIST[@]} GPU render devices"
elif [ -n "$GPU_ENABLED" ]; then
log "INFO" "Wayland client GPU annotation present but disabled: $GPU_ENABLED"
else
log "INFO" "No Wayland client GPU annotation found"
fi
# Iterate over the DEVNAME_LIST to include the required information in the CONTAINER_CONFIG
if [ ${#DEVNAME_LIST[@]} -gt 0 ]; then
log "INFO" "Processing ${#DEVNAME_LIST[@]} GPU devices for Wayland client"
for DEVICE in "${DEVNAME_LIST[@]}"; do
if ! jq -e ".linux.devices[] | select(.path == \"$DEVICE\")" <<<"$CONTAINER_CONFIG" >/dev/null 2>&1; then
# Get device info using device support library
if ! device_info=$(get_device_info "$DEVICE"); then
log "WARNING" "Failed to get device info for $DEVICE, skipping"
continue
fi
# Parse device info: type:major:minor:file_mode:uid:gid
IFS=':' read -r dev_type major minor filemode uid gid <<<"$device_info"
NEW_DEVICE=$(jq -n --arg path "$DEVICE" \
--arg dev_type "$dev_type" \
--arg major "$major" \
--arg minor "$minor" \
--arg filemode "$filemode" \
--arg uid "$uid" \
--arg gid "$gid" \
'{
"path": $path,
"type": $dev_type,
"major": $major|tonumber,
"minor": $minor|tonumber,
"fileMode": $filemode|tonumber,
"uid": $uid|tonumber,
"gid": $gid|tonumber,
}')
NEW_DEV_RESOURCE=$(jq -n \
--arg dev_type "$dev_type" \
--arg major "$major" \
--arg minor "$minor" \
'{
"allow": true,
"type": $dev_type,
"major": $major|tonumber,
"minor": $minor|tonumber,
"access": "rwm"
}')
CONTAINER_CONFIG=$(jq ".linux.devices += [$NEW_DEVICE]" <<<"$CONTAINER_CONFIG")
CONTAINER_CONFIG=$(jq ".linux.resources.devices += [$NEW_DEV_RESOURCE]" <<<"$CONTAINER_CONFIG")
log "INFO" "Added GPU device: $DEVICE"
else
log "INFO" "GPU device already exists in spec: $DEVICE"
fi
done
log "INFO" "Successfully processed all GPU devices for Wayland client"
else
log "INFO" "No GPU devices to process for Wayland client"
fi
# Initialize log file directory
mkdir -p "$(dirname "$LOGFILE")"
touch "$LOGFILE"
# Count total devices in final spec
total_devices=$(echo "$CONTAINER_CONFIG" | jq '.linux.devices | length // 0')
log "INFO" "Total devices in final spec: $total_devices"
log "INFO" "QM Wayland Client Devices hook completed successfully"
echo "$CONTAINER_CONFIG" | jq .

View File

@ -0,0 +1,12 @@
{
"version": "1.0.0",
"hook": {
"path": "/usr/libexec/oci/hooks.d/oci-qm-wayland-client-devices"
},
"when": {
"annotations": {
"^org\\.containers\\.qm\\.wayland-client\\..*$": "^.*$"
}
},
"stages": ["precreate"]
}

18
plans/e2e/aib.fmf Normal file
View File

@ -0,0 +1,18 @@
summary: automotive-image-builder QM build test
discover:
how: fmf
filter: 'tag:aib'
prepare:
- name: Install packages
how: install
order: 20
package:
- jq
execute:
how: tmt
report:
how: junit

36
plans/e2e/ffi.fmf Normal file
View File

@ -0,0 +1,36 @@
summary: FFI - QM FreedomFromInterference
environment+:
CONTROL_CONTAINER_NAME: host
discover:
how: fmf
filter: tag:ffi
provision:
how: local
adjust:
- when: distro == centos-stream-9, fedora
environment+:
FFI_SETUP_OPTIONS: --set-qm-disk-part=yes
- when: scenario == ffi
prepare+:
- name: Set QM env
how: shell
# FIXME: On new QM release remove
# qm-setup-from-gh-url, branch-qm option
script: |
cd tests/e2e
./set-ffi-env-e2e "${FFI_SETUP_OPTIONS}"
- name: Place quadlet for ffi-qm container
how: shell
script: |
cp tests/ffi/common/ffi-qm.container /etc/qm/containers/systemd/
execute:
how: tmt
report:
how: junit

18
plans/e2e/kvm-tier-0.fmf Normal file
View File

@ -0,0 +1,18 @@
summary: Kvm Tier 0 - QM sanity test
discover:
how: fmf
filter: 'tier:0&tag:kvm|tier:0&tag:qmctl-test'
prepare+:
- name: Enable copr and install rpms
script: |
cd tests/e2e
bash ./lib/repoutils
execute:
how: tmt
report:
how: junit

View File

@ -0,0 +1,34 @@
summary: multiple bluechi-agents test - QM Interconnect through bluechi
discover:
how: fmf
filter: tag:multi-bluechi-agents
provision:
how: local
adjust:
- when: distro == centos-stream-9 or distro == fedora
prepare+:
- name: Prepare Repos
how: shell
script: |
dnf install -y dnf-plugin-config-manager epel-release
dnf config-manager -y --set-enabled crb
- name: install repos
how: install
package:
- podman
- name: Set QM env
how: shell
script: |
cd tests/e2e
./run-test-e2e --skip-tests=yes
execute:
how: tmt
report:
how: junit

19
plans/e2e/tier-0.fmf Normal file
View File

@ -0,0 +1,19 @@
summary: Tier 0 - QM sanity test
discover:
how: fmf
filter: 'tier:0&tag:-setup'
prepare+:
- name: Set QM environment
how: shell
order: 50
script: |
cd tests/e2e
./set-ffi-env-e2e "${FFI_SETUP_OPTIONS}"
execute:
how: tmt
report:
how: junit

30
plans/e2e/tier-1.fmf Normal file
View File

@ -0,0 +1,30 @@
summary: Tier 1 - QM Interconnect through bluechi
discover:
how: fmf
filter: tier:1
provision:
# Can not use provision no podman args
how: local
adjust:
prepare+:
- name: Install rpms
how: install
package: podman
- name: Setup AutoSD env
how: shell
script: |
# Currently option passing c9s
podman run --replace -d --name autosd \
--privileged \
quay.io/centos-sig-automotive/autosd:latest
when: distro == centos-stream-9 or distro == fedora
execute:
how: tmt
report:
how: junit

22
plans/main.fmf Normal file
View File

@ -0,0 +1,22 @@
summary: general data used by the test plans
environment:
FFI_SETUP_OPTIONS: none
prepare:
- name: Install podman
how: install
order: 20
package:
- podman
- bc
adjust:
- when: run == manual
environment+:
# Sample code to use manual packit repo
PACKIT_COPR_PROJECT: packit/containers-qm-291
- when: distro == centos-stream-9, fedora
environment+:
CS_DISTRO: $@distro

View File

@ -0,0 +1,10 @@
#!/usr/bin/bash
set -eu
if command -v packit; then
packit -d validate-config
else
echo "packit not installed, can't validate the config"
echo "either install packit or try the validate-config-in-container hook"
fi

80
qm.8.md
View File

@ -1,9 +1,11 @@
% QM 8
## NAME
QM - Set up a Containerized environment for running Functional Safety QM (Quality Management) software.
## SYNOPSIS
This package allows users to set up an environment that prevents applications
and container tools from interfering with other processes on the
system.
@ -22,12 +24,12 @@ use container tools like Podman.
After the QM software package is installed, execute the
/usr/share/qm/setup script to setup and install the /usr/lib/qm/rootfs
with packages to run an isolated environment. The setup script installs the
**selinux-policy-targeted**, **podman**, **systemd**, and **hirte** packages.
**selinux-policy-targeted**, **podman**, **systemd**, and **bluechi** packages.
Setup then enables and starts a Podman quadlet service qm.service (qm.container).
This Podman quadlet can be examined with the following command:
```
```console
systemctl status qm.service
● qm.service
Loaded: loaded (/etc/containers/systemd/qm.container; generated)
@ -38,7 +40,7 @@ systemctl status qm.service
Tasks: 11 (limit: 76801)
Memory: 275.1M (swap max: 0B)
CPU: 4.527s
CGroup: /QM.slice/qm.service
CGroup: /qm.service
├─libpod-payload-00de006493bc970788d6c830beb494a58a9a2847a5eda200812d3a8b4e214814
│ ├─init.scope
│ │ └─993676 /sbin/init
@ -51,18 +53,20 @@ systemctl status qm.service
...
```
## CGROUPS QM.slice
## CGroups and container configuration
Notice that the QM environment is running systemd and other services within the
QM.Slice. This slice can be used to modify the cgroups controls of all of the
processes within the QM environment.
The options in the qm.container file overridden by using drop-in files, in the
directories `/etc/containers/systemd/qm.container.d` or`
`/usr/lib/containers/systemd/qm.container.d. This allows overriding for example
CGroup options like Service.CPUWeight, or podman options like Container.Volume.
Such options will affect all the processes running in the qm container.
## Install Additional packages in QM
If other packages need to be added into the QM environment, use the `dnf` command
on the host. For example, the following example installs the dnf command into the QM environment:
```
```console
# dnf install --installroot=/usr/lib/qm/rootfs dnf
Unable to read consumer identity
@ -78,16 +82,17 @@ Installing:
## Entering the QM
To enter the QM environment, use this Podman command to
To enter the QM environment, use this Podman command to
launch containers within it.
```
```console
sh-5.2# podman exec -ti qm sh
sh-5.2#
```
The SELinux label can be checked by executing the following:
```
```console
sh-5.2# id -Z
system_u:system_r:qm_t:s0:c35,c404
```
@ -97,14 +102,14 @@ confined QM process within the QM environment.
Containers can now be run within the QM environment using Podman.
```
```console
sh-5.2# podman run --rm ubi9-minimal echo hi
Resolved "ubi9-minimal" as an alias (/etc/containers/registries.conf.d/000-shortnames.conf)
Trying to pull registry.access.redhat.com/ubi9-minimal:latest...
Getting image source signatures
Checking if image destination supports signatures
Copying blob 7bffb309b4e8 done
Copying config 96179718b4 done
Copying blob 7bffb309b4e8 done
Copying config 96179718b4 done
Writing manifest to image destination
Storing signatures
hi
@ -115,5 +120,50 @@ applications within the QM. All applications within the QM environment are
prevented from interfering with applications running outside of the QM
environment.
## Configuring bluechi agent in the QM
The configuration of the hosts /etc/bluechi/agent.conf file is copied into the QM every time the
qm.service is started, with the nodename of the hosts agent.conf modified by prepending `qm.`
on the front of the nodename. If the hosts /etc/bluechi/agent.conf does not exists, then the
QM bluechi agent will default to `qm.`$(hostname).
If you want permanently modify the bluechi agent within the QM you can add config to
/usr/lib/qm/rootfs/etc/bluechi/agent.conf.d/ directory or modify the /etc/containers/systemd/qm.container
quadlet file to not execute the bluechi-agent setup script.
## Using systemd drop-in with QM
The systemd drop-in feature allows users to extend or modify the configuration of systemd units without directly editing the unit files provided by the system package.
In this example, we will add the AllowedCPU to set as 1 to qm.service that quadlet generated:
### Create allowedcpus.conf
```console
cat /etc/systemd/system/qm.service.d/allowedcpus.conf
# Contents of qm.continer.d/allowedcpus.conf
[Service]
AllowedCPUs=1
```
## Tools
### qm-rootfs
Prints the qm rootfs location previously configured during setup.
### qm-storage-settings
Setup the initial QM configuration for storage using the follow config files and changes:
- `${ROOTFS}/etc/containers/storage.conf`
- uncomment `additionalimagestores`
- add `/var/lib/shared` into `additionalimagestores`
- uncomment and set to `true` the option `transient_store`
- `${ROOTFS}/etc/containers/container.conf`
- add `[engine]` and `TMPDIR`
## SEE ALSO
**[podman(1)](https://github.com/containers/podman/blob/main/docs/source/markdown/podman.1.md)**, **[quadlet(5)](https://github.com/containers/podman/blob/main/docs/source/markdown/podman-systemd.unit.5.md)**, systemctl(1), systemd(1), dnf(8)
**[podman(1)](https://github.com/containers/podman/blob/main/docs/source/markdown/podman.1.md)**,**[quadlet(5)](https://github.com/containers/podman/blob/main/docs/source/markdown/podman-systemd.unit.5.md)**, systemctl(1), systemd(1), dnf(8), [bluechi-agent(1)](https://github.com/containers/bluechi/blob/main/doc/man/bluechi-agent.1.md),[bluechi-agent.conf.5](https://github.com/containers/bluechi/blob/main/doc/man/bluechi-agent.conf.5.md)

View File

@ -1,26 +1,112 @@
[Install]
WantedBy=default.target
[Service]
AllowedCPUs=6-11
CPUWeight=50
# It's recommended to use systemd drop-in to override the
# systemd settings. See QM manpage for an example.
# CPUWeight: This setting controls the CPU controller for qm.
# Delegate: Turns on delegation of further resource control
# partitioning to processes of the unit.
# IOWeight: Set the overall block I/O weight for qm.
# ManagedOOMSwap=auto|kill: Specifies how systemd-oomd.service will act on qm.
# QM cgroup, pass directly to systemd and handled by it,
# please refer to `man systemd.resource-control` for details.
CPUWeight=idle
Delegate=true
IOWeight=50
ManagedOOMSwap=kill
# MemoryMax
# -----------
# Default is infinity - sets no upper bound on memory usage, allowing the
# service to consume as much memory as the system allows, just like
# MemoryMax=0 or omitting it.
MemoryMax=infinity
# MemoryHigh
# -----------
# Default is infinity - Disables the soft memory limit, meaning no throttling
# will occur due to high memory usage, similar to MemoryHigh=0 or
# omitting it.
MemoryHigh=infinity
MemorySwapMax=0
# Containers within the qm y default set OOMScoreAdj to 750
OOMScoreAdjust=500
# Containers within the qm contain default set OOMScoreAdj to 750
OOMScoreAdjust=500
Restart=always
Slice=QM.slice
# qm.service is a toplevel cgroup, so CPUWeight is relative to all other cgroups in that
# parent (such as user.slice and system.slice), otherwise the CPUWeight of qm.service
# is only compared to the other children of its parent.
Slice=-.slice
Environment=ROOTFS=/usr/lib/qm/rootfs
Environment=RWETCFS=/etc/qm
Environment=RWVARFS=/var/qm
LimitNOFILE=65536
TasksMax=50%
[Container]
# AddCapability
# -------------
# Add these capabilities, in addition to the default Podman capability set, to the container.
# If set to all, grants all capabilities to the container, increasing flexibility but significantly
# reducing security.
# For details see: https://docs.podman.io/en/latest/markdown/podman-systemd.unit.5.html#addcapability
AddCapability=all
SecurityLabelNested=true
SeccompProfile=/usr/share/qm/seccomp-no-rt.json
# PidsLimit
# ---------
# Disables the PID limit for the container by setting it to -1.
# Without a limit, the container can spawn unlimited processes, potentially exhausting system resources.
# For details see: https://docs.podman.io/en/latest/markdown/podman-systemd.unit.5.html#pidslimit
PidsLimit=-1
# Comment DropCapability this will allow FFI Tools to surpass their defaults.
DropCapability=sys_boot sys_resource
AddDevice=-/dev/kvm
AddDevice=-/dev/fuse
ContainerName=qm
Exec=/sbin/init
Network=host
PodmanArgs=--security-opt label=nested --security-opt unmask=all
Network=private
# ReadOnly
# --------
# Makes the container's filesystem read-only, enhancing security by preventing modifications.
ReadOnly=true
Rootfs=/usr/lib/qm/rootfs
# TmpFS flags
ReadOnlyTmpfs=false
Mount=type=tmpfs,tmpfs-size=512M,destination=/tmp
Mount=type=tmpfs,tmpfs-size=512M,destination=/run
Mount=type=tmpfs,destination=/dev/shm
# Rootfs
# ------
# Defines the root filesystem location for QM partition.
# By default the '${ROOTFS}' variable points to /usr/lib/qm/rootfs.
# For details see: https://docs.podman.io/en/latest/markdown/podman-systemd.unit.5.html#rootfs
#
Rootfs=${ROOTFS}
# The value for fs.mqueue.queues_max determines the maximum number of POSIX message queues
# that can be created system-wide within the container. This value is set based on available
# system resources and the expected usage pattern. The calculation is approximately:
# queues_max ≈ (system-wide RLIMIT_MSGQUEUE) / (msg_max * msgsize_max) / 2
# where:
# - RLIMIT_MSGQUEUE is the total bytes allowed for all message queues (ulimit -q)
# - msg_max is the maximum number of messages allowed per queue (msg_max)
# - msgsize_max is the maximum size of each message (msgsize_max)
# The division by 2 provides a safety margin to avoid exhausting resources and grant FFI.
Sysctl=fs.mqueue.queues_max=4
SecurityLabelNested=true
SecurityLabelFileType=qm_file_t
SecurityLabelLevel=s0
SecurityLabelType=qm_t
Volume=qmEtc:/etc:copy
Volume=qmVar:/var:copy
Timezone=local
Volume=${RWETCFS}:/etc
Volume=${RWVARFS}:/var

9
qm.fc
View File

@ -6,3 +6,12 @@
/usr/lib/qm/rootfs/var/lib/containers/storage/overlay2-layers(/.*)? gen_context(system_u:object_r:qm_container_ro_file_t,s0)
/usr/lib/qm/rootfs/var/lib/containers/storage/overlay-images(/.*)? gen_context(system_u:object_r:qm_container_ro_file_t,s0)
/usr/lib/qm/rootfs/var/lib/containers/storage/overlay2-images(/.*)? gen_context(system_u:object_r:qm_container_ro_file_t,s0)
/var/qm(/.*)? gen_context(system_u:object_r:qm_file_t,s0)
/etc/qm(/.*)? gen_context(system_u:object_r:qm_file_t,s0)
# File context for ipc programs
/usr/lib/qm/rootfs/run/ipc(/.*)? gen_context(system_u:object_r:ipc_var_run_t,s0)
/run/ipc(/.*)? gen_context(system_u:object_r:ipc_var_run_t,s0)
# File context for bluechi-agent inside QM
/usr/lib/qm/rootfs/usr/libexec/bluechi-agent -- gen_context(system_u:object_r:qm_bluechi_agent_exec_t,s0)

245
qm.if
View File

@ -15,14 +15,15 @@ template(`qm_domain_template',`
gen_require(`
class dbus { send_msg acquire_svc };
class passwd rootok;
class process setcurrent;
attribute container_domain;
attribute filesystem_type;
attribute container_init_domain;
attribute container_net_domain;
attribute container_user_domain;
attribute unconfined_domain_type;
type ipc_t;
type ipc_var_run_t;
type cgroup_t;
type container_runtime_t;
type devpts_t;
@ -37,19 +38,28 @@ template(`qm_domain_template',`
type sysctl_irq_t;
type sysctl_t;
type system_dbusd_t;
type systemd_hostnamed_t;
type systemd_logind_t;
type systemd_machined_t;
type unconfined_service_t;
type bpf_t;
type container_devpts_t;
type net_conf_t;
type getty_t;
')
type $1_t;
domain_type($1_t)
role system_r types $1_t;
unconfined_stub_role()
role unconfined_r types $1_t;
init_initrc_domain($1_t)
container_use_ptys($1_t)
container_read_share_files($1_t)
container_exec_share_files($1_t)
allow $1_t container_ro_file_t:file execmod;
allow $1_container_domain $1_file_type:chr_file { rw_inherited_file_perms };
allow $1_t self:process setcurrent;
attribute $1_file_type;
allow $1_file_type self:filesystem associate;
@ -71,6 +81,12 @@ template(`qm_domain_template',`
manage_files_pattern($1_t, $1_file_type, $1_file_type)
can_exec($1_t, $1_file_type)
allow $1_t $1_file_type:chr_file mounton;
allow $1_t $1_file_type:sock_file mounton;
filetrans_pattern(ipc_t, $1_file_t, ipc_var_run_t, dir, "ipc")
list_dirs_pattern($1_t, ipc_var_run_t, ipc_var_run_t)
allow $1_t ipc_var_run_t:dir mounton;
manage_blk_files_pattern($1_t, $1_file_type, $1_file_type)
manage_chr_files_pattern($1_t, $1_file_type, $1_file_type)
manage_dirs_pattern($1_t, $1_file_type, $1_file_type)
@ -78,12 +94,17 @@ template(`qm_domain_template',`
manage_lnk_files_pattern($1_t, $1_file_type, $1_file_type)
manage_sock_files_pattern($1_t, $1_file_type, $1_file_type)
fs_tmpfs_filetrans($1_t, $1_file_t, { dir file lnk_file })
allow $1_t $1_file_type:chr_file { watch watch_reads };
allow $1_t $1_file_type:chr_file { watch watch_reads map };
allow $1_t $1_file_type:dir { mounton relabelfrom relabelto };
allow $1_t $1_file_type:filesystem all_filesystem_perms;
allow $1_t $1_file_type:service all_service_perms;
container_read_share_files($1_container_domain)
container_exec_share_files($1_container_domain)
allow $1_container_domain container_ro_file_t:file execmod;
allow init_t $1_file_type:file read_file_perms;
manage_blk_files_pattern(init_t, $1_file_type, $1_file_type)
manage_chr_files_pattern(init_t, $1_file_type, $1_file_type)
manage_dirs_pattern(init_t, $1_file_type, $1_file_type)
@ -98,8 +119,8 @@ template(`qm_domain_template',`
filetrans_pattern($1_t, $1_container_var_lib_t, $1_container_ro_file_t, dir, "overlay2")
filetrans_pattern($1_t, $1_container_var_lib_t, $1_container_ro_file_t, dir, "overlay2-imagess")
filetrans_pattern($1_t, $1_container_var_lib_t, $1_container_ro_file_t, dir, "overlay2-layers")
allow $1_container_domain $1_container_ro_file_t:file execmod;
allow container_domain $1_container_ro_file_t:file execmod;
ps_process_pattern(systemd_machined_t, $1_t)
read_files_pattern(systemd_machined_t, $1_file_type, $1_file_type)
list_dirs_pattern(systemd_machined_t, $1_file_type, $1_file_type)
@ -107,8 +128,8 @@ template(`qm_domain_template',`
rw_sock_files_pattern(systemd_machined_t, $1_file_type, $1_file_type)
manage_chr_files_pattern(systemd_machined_t, $1_file_type, $1_file_type)
allow systemd_machined_t $1_t:unix_stream_socket { connectto rw_stream_socket_perms };
allow system_dbusd_t $1_file_type:chr_file { read write };
allow systemd_machined_t unconfined_service_t:dir search;
allow system_dbusd_t $1_file_type:chr_file rw_chr_file_perms;
allow systemd_machined_t unconfined_service_t:dir search_dir_perms;
systemd_dbus_chat_machined($1_t)
allow systemd_machined_t self:cap_userns kill;
@ -120,13 +141,13 @@ template(`qm_domain_template',`
manage_chr_files_pattern(systemd_logind_t, $1_file_type, $1_file_type)
allow systemd_logind_t $1_t:unix_stream_socket { connectto rw_stream_socket_perms };
allow system_dbusd_t $1_file_type:chr_file { read write };
allow system_dbusd_t $1_file_type:chr_file rw_chr_file_perms;
allow $1_t self:system all_system_perms;
allow $1_t self:user_namespace all_user_namespace_perms;
allow $1_t self:bpf { map_create map_read map_write prog_load prog_run };
allow $1_t self:cap_userns { audit_write chown dac_override dac_read_search fowner fsetid kill net_bind_service net_admin net_raw setfcap setgid setpcap setuid sys_admin sys_boot sys_chroot sys_ptrace sys_resource };
allow $1_t self:capability { audit_write chown dac_override dac_read_search fowner fsetid kill net_bind_service net_admin net_raw setfcap setgid setpcap setuid sys_admin sys_boot sys_chroot sys_ptrace sys_resource };
allow $1_t self:capability { audit_write chown dac_override dac_read_search fowner fsetid ipc_lock kill net_bind_service net_admin net_raw setfcap setgid setpcap setuid sys_admin sys_boot sys_chroot sys_nice sys_ptrace sys_resource sys_tty_config };
allow $1_t self:capability2 { audit_read bpf perfmon};
allow $1_t self:packet_socket create_socket_perms;
@ -154,15 +175,24 @@ template(`qm_domain_template',`
seutil_search_default_contexts($1_t)
allow $1_t bpf_t:dir mounton;
allow $1_t cgroup_t:filesystem { getattr remount};
allow $1_t cgroup_t:{dir file } mounton;
allow $1_t container_devpts_t:chr_file { watch watch_reads };
allow $1_t container_runtime_t:fifo_file rw_fifo_file_perms;
allow $1_t devpts_t:filesystem relabelfrom;
allow $1_t hugetlbfs_t:dir relabelfrom;
allow $1_t mtrr_device_t:file { getattr mounton };
allow $1_t proc_kcore_t:file { getattr mounton };
allow $1_t proc_kmsg_t:file { getattr mounton };
allow $1_t proc_t:file mounton;
allow $1_t security_t:dir read;
allow $1_t sysctl_irq_t:dir { getattr mounton };
allow $1_t sysctl_t:file { getattr mounton };
allow $1_t cgroup_t:filesystem { getattr remount };
allow $1_t container_devpts_t:chr_file { watch watch_reads };
allow $1_t devpts_t:filesystem relabelfrom;
corecmd_entrypoint_all_executables($1_t)
corecmd_exec_bin($1_t)
corecmd_exec_shell($1_t)
corenet_icmp_bind_generic_node($1_t)
corenet_raw_bind_generic_node($1_t)
@ -177,13 +207,17 @@ template(`qm_domain_template',`
corenet_udp_bind_generic_node($1_t)
corenet_udp_sendrecv_all_ports($1_t)
dev_dontaudit_mounton_sysfs($1_container_domain)
dev_getattr_mtrr_dev($1_container_domain)
dev_list_sysfs($1_container_domain)
dev_list_sysfs($1_t)
dev_mounton_sysfs($1_t)
dev_mounton_sysfs($1_t)
dev_read_rand($1_t)
dev_read_sysfs($1_t)
dev_read_urand($1_t)
dev_remount_sysfs_fs($1_t)
allow $1_t bpf_t:dir mounton;
allow $1_t container_runtime_t:fifo_file write;
dev_write_sysfs_dirs($1_t)
files_getattr_all_blk_files($1_t)
files_getattr_all_chr_files($1_t)
@ -206,8 +240,12 @@ template(`qm_domain_template',`
fs_relabelfrom_tmpfs($1_t)
fs_relabelfrom_xattr_fs($1_t)
fs_search_tracefs_dirs($1_t)
fs_set_xattr_fs_quotas($1_t)
allow $1_t nsfs_t:filesystem { getattr unmount };
domain_obj_id_change_exemption($1_t)
kernel_dgram_send($1_t)
kernel_dontaudit_search_security_state($1_t)
kernel_list_all_proc($1_t)
kernel_mounton_core_if($1_t)
@ -232,17 +270,25 @@ template(`qm_domain_template',`
kernel_rw_net_sysctls($1_t)
kernel_rw_security_state($1_t)
kernel_rw_unix_sysctls($1_t)
kernel_rw_vm_sysctls($1_t)
kernel_rw_usermodehelper_state($1_t)
kernel_rw_vm_sysctls($1_t)
kernel_search_debugfs($1_t)
dontaudit $1_t proc_security_t:file write;
allow $1_t filesystem_type:filesystem { mount remount unmount };
kernel_search_debugfs($1_t)
unconfined_dgram_send($1_t)
selinux_compute_access_vector($1_t)
selinux_compute_create_context($1_t)
selinux_dontaudit_get_fs_mount($1_t)
selinux_dontaudit_search_fs($1_t)
selinux_get_enforce_mode($1_t)
selinux_mounton_fs($1_t)
selinux_setcheckreqprot($1_t)
selinux_validate_context($1_t)
dontaudit $1_t security_t:file write;
dontaudit $1_t security_t:security read_policy;
sysnet_read_config($1_t)
sysnet_write_config($1_t)
@ -251,16 +297,7 @@ template(`qm_domain_template',`
term_use_generic_ptys($1_t)
term_setattr_generic_ptys($1_t)
dev_write_sysfs_dirs($1_t)
allow $1_t security_t:dir read;
allow $1_t hugetlbfs_t:dir relabelfrom;
dontaudit $1_t security_t:security read_policy;
selinux_compute_access_vector($1_t)
selinux_compute_create_context($1_t)
selinux_get_enforce_mode($1_t)
selinux_validate_context($1_t)
userdom_use_inherited_user_ptys($1_t)
allow container_runtime_t $1_t:process { dyntransition transition };
allow $1_t container_runtime_t:process sigchld;
@ -290,18 +327,26 @@ template(`qm_domain_template',`
domain_user_exemption_target($1_container_t)
container_manage_files_template($1_container, $1_container)
type $1_container_ipc_t, $1_container_domain;
domain_type($1_container_ipc_t)
domain_user_exemption_target($1_container_ipc_t)
container_manage_files_template($1_container_ipc, $1_container)
container_ipc_stream_connect($1_container_ipc_t)
container_stream_connect($1_container_ipc_t)
type $1_container_file_t, $1_file_type;
files_type($1_container_file_t)
files_mountpoint($1_container_file_t)
fs_associate($1_container_file_t)
allow $1_container_domain $1_file_type:file { execmod relabelfrom relabelto map entrypoint mounton };
allow $1_container_domain $1_file_type:file { execmod relabelfrom relabelto map entrypoint mounton};
allow $1_container_domain $1_file_type:dir search_dir_perms;
exec_files_pattern($1_container_domain, $1_file_type, $1_file_type)
list_dirs_pattern($1_container_domain, $1_file_type, $1_file_type)
read_files_pattern($1_container_domain, $1_file_type, $1_file_type)
# QM Container kvm - Policy for running kata containers
type $1_container_kvm_t, $1_container_domain;
domain_type($1_container_kvm_t)
domain_user_exemption_target($1_container_kvm_t)
typeattribute $1_container_kvm_t container_net_domain, container_user_domain;
container_manage_files_template($1_container_kvm, $1_container)
filetrans_pattern($1_container_t, $1_file_t, $1_container_file_t, sock_file)
qm_container_template($1, kvm)
type $1_container_kvm_var_run_t;
files_pid_file($1_container_kvm_var_run_t)
@ -317,12 +362,16 @@ template(`qm_domain_template',`
files_pid_filetrans($1_container_kvm_t, $1_container_kvm_var_run_t, { dir file lnk_file sock_file })
allow $1_container_kvm_t $1_container_kvm_var_run_t:{file dir} mounton;
allow $1_container_kvm_t $1_t:unix_stream_socket rw_stream_socket_perms;
manage_files_pattern($1_container_kvm_t, $1_file_t, $1_file_t)
manage_sock_files_pattern($1_container_kvm_t, $1_file_t, $1_file_t)
allow $1_container_kvm_t $1_container_wayland_t:unix_stream_socket rw_stream_socket_perms;
allow $1_container_kvm_t $1_t:unix_stream_socket { connectto rw_stream_socket_perms };
container_stream_connect($1_container_kvm_t)
allow $1_container_kvm_t $1_t:tun_socket attach_queue;
dev_read_sysfs($1_container_kvm_t)
dev_rw_inherited_vhost($1_container_kvm_t)
dev_rw_vfio_dev($1_container_kvm_t)
@ -352,32 +401,29 @@ template(`qm_domain_template',`
sssd_read_public_files($1_container_kvm_t)
# Container init - Policy for running systemd based containers
type $1_container_init_t, $1_container_domain;
domain_type($1_container_init_t)
domain_user_exemption_target($1_container_init_t)
typeattribute $1_container_init_t container_init_domain, container_net_domain, container_user_domain;
corenet_unconfined($1_container_init_t)
qm_container_template($1, init)
logging_send_syslog_msg($1_container_init_t)
allow $1_container_init_t proc_t:filesystem remount;
qm_container_template($1, wayland)
optional_policy(`
virt_default_capabilities($1_container_init_t)
')
allow $1_container_wayland_t $1_file_t:chr_file map;
manage_dirs_pattern($1_container_wayland_t, $1_file_t, $1_file_t)
manage_files_pattern($1_container_wayland_t, $1_file_t, $1_file_t)
manage_sock_files_pattern($1_container_wayland_t, $1_file_t, $1_file_t)
allow $1_container_wayland_t $1_t:unix_stream_socket connectto;
allow $1_container_wayland_t $1_t:dbus send_msg;
allow $1_t $1_container_wayland_t:dbus send_msg;
dev_read_sysfs($1_container_wayland_t)
tunable_policy(`virt_sandbox_use_sys_admin',`
allow $1_container_init_t self:capability sys_admin;
allow $1_container_init_t self:cap_userns sys_admin;
')
allow getty_t $1_file_type:chr_file rw_chr_file_perms;
allow $1_container_init_t self:netlink_audit_socket nlmsg_relay;
container_manage_files_template($1_container_init, $1_container)
read_files_pattern(systemd_hostnamed_t, $1_file_t, $1_file_t)
systemd_dbus_chat_hostnamed(systemd_hostnamed_t)
read_files_pattern($1_container_t, $1_container_ro_file_t,$1_container_ro_file_t,)
read_lnk_files_pattern($1_container_t, $1_container_ro_file_t,$1_container_ro_file_t,)
list_dirs_pattern($1_container_t, $1_container_ro_file_t,$1_container_ro_file_t,)
read_files_pattern($1_container_domain, $1_container_ro_file_t,$1_container_ro_file_t)
read_lnk_files_pattern($1_container_domain, $1_container_ro_file_t,$1_container_ro_file_t)
list_dirs_pattern($1_container_domain, $1_container_ro_file_t,$1_container_ro_file_t)
#
# Rules for container domains in the qm
@ -406,7 +452,7 @@ template(`qm_domain_template',`
allow $1_container_domain self:packet_socket create_socket_perms;
allow $1_container_domain self:passwd rootok;
allow $1_container_domain self:peer recv;
allow $1_container_domain self:process all_process_perms;
allow $1_container_domain self:process { execmem execstack fork getattr getcap getpgid getsched getsession setcap setpgid setrlimit setsched sigchld sigkill signal signull sigstop};
allow $1_container_domain self:sem create_sem_perms;
allow $1_container_domain self:shm create_shm_perms;
allow $1_container_domain self:socket_class_set { create_socket_perms map accept };
@ -423,6 +469,7 @@ template(`qm_domain_template',`
allow $1_t $1_container_domain:process { dyntransition transition };
allow $1_t $1_container_domain:process2 { nnp_transition nosuid_transition };
allow $1_t $1_container_domain:tun_socket relabelfrom;
allow $1_container_domain $1_t:unix_dgram_socket sendto;
allow $1_container_domain container_runtime_t:unix_dgram_socket sendto;
allow $1_container_domain container_runtime_tmpfs_t:dir mounton;
@ -439,11 +486,14 @@ template(`qm_domain_template',`
allow unconfined_domain_type $1_container_domain:process2 { nnp_transition nosuid_transition };
allow unconfined_service_t $1_container_domain:process dyntransition;
dev_getattr_all($1_container_domain)
dev_list_sysfs($1_container_domain)
dev_dontaudit_mounton_sysfs($1_container_domain)
domain_dontaudit_link_all_domains_keyrings($1_container_domain)
domain_dontaudit_search_all_domains_keyrings($1_container_domain)
domain_dontaudit_search_all_domains_state($1_container_domain)
dontaudit $1_container_domain container_runtime_tmpfs_t:dir read;
dontaudit $1_container_domain $1_t:chr_file getattr;
dontaudit $1_container_domain $1_container_domain:key search;
dontaudit $1_container_domain self:capability fsetid;
dontaudit $1_container_domain self:capability2 block_suspend ;
@ -526,4 +576,95 @@ template(`qm_domain_template',`
userdom_rw_inherited_user_pipes($1_container_domain)
userdom_use_user_ptys($1_container_domain)
optional_policy(`
vsomeip_use($1_t)
vsomeip_use($1_container_domain)
')
')
########################################
## <summary>
## Creates types and rules for a basic
## container runtime process domain.
## </summary>
## <param name="prefix">
## <summary>
## Prefix for the domain.
## </summary>
## </param>
#
interface(`vsomeip_use',`
gen_require(`
type vsomeip_t;
type vsomeip_var_run_t;
type router_vsomeip_var_run_t;
')
# create and use vsomeip sockets:
allow $1 vsomeip_var_run_t:dir { add_name remove_name write };
allow $1 vsomeip_var_run_t:sock_file { create setattr write unlink };
# Talk to routing manager (and back)
allow $1 vsomeip_t:unix_stream_socket connectto;
allow vsomeip_t $1:unix_stream_socket connectto;
allow $1 router_vsomeip_var_run_t:sock_file write;
')
########################################
## <summary>
## Creates types and rules for QM a
## container runtime process domain.
## </summary>
## <param name="prefix">
## <summary>
## Prefix for the domain.
## </summary>
## </param>
## <param name="type">
## <summary>
## type of process domain.
## </summary>
## </param>
#
interface(`qm_container_template',`
# Container $2 - Policy for running systemd based containers
type $1_container_$2_t, $1_container_domain;
domain_type($1_container_$2_t)
domain_user_exemption_target($1_container_$2_t)
typeattribute $1_container_$2_t container_net_domain, container_user_domain;
corenet_unconfined($1_container_$2_t)
allow $1_container_$2_t proc_t:filesystem remount;
optional_policy(`
virt_default_capabilities($1_container_$2_t)
')
allow $1_container_$2_t self:netlink_audit_socket nlmsg_relay;
container_manage_files_template($1_container_$2, $1_container)
read_files_pattern($1_container_$2_t, $1_container_ro_file_t, $1_container_ro_file_t)
read_lnk_files_pattern($1_container_$2_t, $1_container_ro_file_t, $1_container_ro_file_t)
list_dirs_pattern($1_container_$2_t, $1_container_ro_file_t, $1_container_ro_file_t)
')
########################################
## <summary>
## Connect to IPC containers over a unix stream socket.
## </summary>
## <param name="domain">
## <summary>
## Domain allowed access.
## </summary>
## </param>
#
interface(`container_ipc_stream_connect',`
gen_require(`
type ipc_t, ipc_var_run_t;
')
files_search_pids($1)
stream_connect_pattern($1, ipc_var_run_t, ipc_var_run_t, ipc_t)
rw_sock_files_pattern($1, ipc_var_run_t, ipc_var_run_t)
')

View File

@ -1,118 +0,0 @@
# For automatic rebuilds in COPR
# The following tag is to get correct syntax highlighting for this file in vim text editor
# vim: syntax=spec
%global debug_package %{nil}
# Some bits borrowed from the openstack-selinux package
%global selinuxtype targeted
%global moduletype services
%global modulenames qm
%global _installscriptdir %{_prefix}/lib/qm
# Usage: _format var format
# Expand 'modulenames' into various formats as needed
# Format must contain '$x' somewhere to do anything useful
%global _format() export %1=""; for x in %{modulenames}; do %1+=%2; %%1+=" "; done;
Name: {{{ git_dir_name }}}
Epoch: 101
Version: {{{ git_dir_version }}}
Release: 1%{?dist}
License: GPLv2
URL: https://github.com/containers/qm
Summary: Containerized environment for running functionally safe QM (Quality Management) software.
VCS: {{{ git_dir_vcs }}}
Source: {{{ git_dir_pack }}}
BuildArch: noarch
BuildRequires: go-md2man
BuildRequires: container-selinux
BuildRequires: make
BuildRequires: git-core
BuildRequires: pkgconfig(systemd)
BuildRequires: selinux-policy >= %_selinux_policy_version
BuildRequires: selinux-policy-devel >= %_selinux_policy_version
Requires: selinux-policy >= %_selinux_policy_version
Requires(post): selinux-policy-base >= %_selinux_policy_version
Requires(post): selinux-policy-targeted >= %_selinux_policy_version
Requires(post): policycoreutils
Requires(post): libselinux-utils
Requires: podman >= 5:4.5
Requires: hirte-agent
%description
This package allow users to setup an environment which prevents applications
and container tools from interfering with other all other processes on the
system.
The QM runs its own version of systemd and Podman to isolate not only the
applications and containers launched by systemd and Podman but systemd and
Podman themselves.
Software install into the QM environment under /usr/lib/qm/rootfs is
automatically isolated from the host. If developers need to further
isolate there applications from other processes in the QM they should
use container tools like Podman.
%prep
{{{ git_dir_setup_macro }}}
sed -i 's/install: man/install:/' Makefile
# Remove unavailable tokens
%if 0%{?fedora} <= 37 || 0%{?rhel} <= 9
sed -i '/user_namespace/d' qm.if
%endif
%build
%{__make}
%install
# install policy modules
%_format MODULES $x.pp.bz2
%{__make} DESTDIR=%{buildroot} DATADIR=%{_datadir} install
%pre
%post
# Install all modules in a single transaction
%_format MODULES %{_datadir}/selinux/packages/$x.pp.bz2
%selinux_modules_install -s %{selinuxtype} $MODULES
# Set AllowedCPUs in quadlet file
NPROC=$(nproc)
if [[ $NPROC == 2 ]]; then
ALLOWED_CPUS=1
else
ALLOWED_CPUS=$(expr $NPROC / 2)"-"$(expr $NPROC - 1)
fi
sed -i "s/^AllowedCPUs=.*/AllowedCPUs=$ALLOWED_CPUS/" %{_datadir}/containers/systemd/qm.container
%postun
if [ $1 -eq 0 ]; then
%selinux_modules_uninstall -s %{selinuxtype} %{modulenames}
fi
%posttrans
#define license tag if not already defined
%{!?_licensedir:%global license %doc}
%files
%doc README.md
%dir %{_datadir}/selinux
%{_datadir}/selinux/*
%dir %{_datadir}/qm
%{_datadir}/qm/containers.conf
%{_datadir}/qm/contexts
%{_datadir}/qm/file_contexts
%{_datadir}/qm/setup
%ghost %dir %{_datadir}/containers
%ghost %dir %{_datadir}/containers/systemd
%config(noreplace) %{_datadir}/containers/systemd/qm.container
%{_mandir}/man8/*
%changelog
{{{ git_dir_changelog }}}

84
qm.te
View File

@ -1,3 +1,85 @@
policy_module(qm, 0.1.0)
policy_module(qm, 0.9)
gen_require(`
attribute container_file_type;
attribute container_runtime_domain;
type init_t;
')
type ipc_t;
domain_type(ipc_t)
role system_r types ipc_t;
unconfined_domain_noaudit(ipc_t)
type ipc_exec_t;
application_executable_file(ipc_exec_t)
allow ipc_t { ipc_exec_t container_file_type}:file entrypoint;
init_system_domain(ipc_t, ipc_exec_t)
role system_r types ipc_t;
domtrans_pattern(container_runtime_domain, ipc_exec_t, ipc_t)
type ipc_var_run_t;
files_pid_file(ipc_var_run_t)
files_mountpoint(ipc_var_run_t)
files_pid_filetrans(ipc_t, ipc_var_run_t, { dir file lnk_file sock_file })
files_pid_filetrans(init_t, ipc_var_run_t, dir, "ipc")
unconfined_domain(ipc_t)
qm_domain_template(qm)
#########################################
#
# bluechi-agent inside QM
#
type qm_bluechi_agent_t;
type qm_bluechi_agent_exec_t;
init_daemon_domain(qm_bluechi_agent_t, qm_bluechi_agent_exec_t)
allow qm_bluechi_agent_t qm_file_t:chr_file read;
allow qm_bluechi_agent_t qm_file_t:dir { open read search getattr };
allow qm_bluechi_agent_t qm_file_t:file { execute getattr open read };
allow qm_bluechi_agent_t qm_file_t:file map;
allow qm_bluechi_agent_t qm_file_t:lnk_file read;
allow qm_bluechi_agent_t qm_file_t:sock_file write;
allow qm_bluechi_agent_t qm_t:unix_dgram_socket sendto;
allow qm_bluechi_agent_t qm_t:unix_stream_socket connectto;
allow qm_bluechi_agent_t self:unix_dgram_socket { create getopt setopt };
allow qm_bluechi_agent_t self:tcp_socket create_stream_socket_perms;
allow qm_bluechi_agent_t qm_t:dbus { send_msg acquire_svc };
allow qm_bluechi_agent_t qm_t:system status;
allow qm_bluechi_agent_t qm_t:system { reload start stop status };
allow qm_bluechi_agent_t qm_file_t:service { reload start stop status };
allow qm_t qm_bluechi_agent_t:dir search;
allow qm_t qm_bluechi_agent_t:file { getattr ioctl open read };
allow qm_t qm_bluechi_agent_t:lnk_file read;
allow qm_t qm_bluechi_agent_t:dbus send_msg;
allow qm_t qm_bluechi_agent_t:process { signull signal sigkill };
unconfined_server_stream_connectto(qm_bluechi_agent_t)
# Allow qm_bluechi_agent_t to connect to any port instead of labelled ones.
gen_tunable(qm_bluechi_agent_port_connect_any, true)
optional_policy(`
require{
type bluechi_var_run_t;
type bluechi_agent_port_t;
type bluechi_t;
}
tunable_policy(`qm_bluechi_agent_port_connect_any',`
corenet_tcp_connect_all_ports(qm_bluechi_agent_t)
',`
allow qm_bluechi_agent_t bluechi_agent_port_t:tcp_socket name_connect;
')
stream_connect_pattern(qm_bluechi_agent_t, bluechi_var_run_t, bluechi_var_run_t, bluechi_t)
')

1
rpm/.coprignore Normal file
View File

@ -0,0 +1 @@
qm-kvm.spec

1
rpm/.gitignore vendored Normal file
View File

@ -0,0 +1 @@
*.tar.gz

48
rpm/kvm/qm-kvm.spec Normal file
View File

@ -0,0 +1,48 @@
%global debug_package %{nil}
# rootfs_qm, Define rootfs macro for QM environment not need, do to install command from host
# dnf install --setopt=reposdir=/etc/yum.repos.d <package>
# using qm_sysconfdir /etc/qm/ overlay preventing the detection of quadletfile, need to install
# in the overlay of etc under the host
%define qm_sysconfdir %{_sysconfdir}/qm
Name: qm-kvm
# Version: 0
Version: %{version}
Release: 1%{?dist}
Summary: Drop-in configuration for QM containers to mount bind /dev/kvm
License: GPL-2.0-only
URL: https://github.com/containers/qm
Source0: %{url}/archive/qm-kvm-%{version}.tar.gz
BuildArch: noarch
Requires: qm >= %{version}
%description -n qm-kvm
This subpackage provides a drop-in configuration for the QM environment to enable mount binding of `/dev/kvm` from the host system to containers. This configuration is essential for supporting KVM-based virtualization within QM containers.
%prep
%autosetup -Sgit -n qm-kvm-%{version}
%build
%install
# Create the directory for drop-in configurations
install -d %{buildroot}%{_sysconfdir}/containers/systemd/qm.container.d
install -d %{buildroot}%{qm_sysconfdir}/containers/systemd
# Install the KVM drop-in configuration file
install -m 644 %{_builddir}/qm-kvm-%{version}/etc/containers/systemd/qm.container.d/qm_dropin_mount_bind_kvm.conf \
%{buildroot}%{_sysconfdir}/containers/systemd/qm.container.d/qm_dropin_mount_bind_kvm.conf
install -m 644 %{_builddir}/qm-kvm-%{version}/subsystems/kvm/etc/containers/systemd/kvm.container \
%{buildroot}%{qm_sysconfdir}/containers/systemd/kvm.container
%files -n qm-kvm
%license LICENSE
%doc README.md SECURITY.md
%{_sysconfdir}/containers/systemd/qm.container.d/qm_dropin_mount_bind_kvm.conf
%{qm_sysconfdir}/containers/systemd/kvm.container
%changelog
* Fri Jul 21 2023 RH Container Bot <rhcontainerbot@fedoraproject.org>
- Initial standalone spec for the QM KVM subpackage.

View File

@ -0,0 +1,120 @@
%global debug_package %{nil}
# Define path macro for QM rootfs
%global qm_rootfs_prefix /usr/lib/qm/rootfs
Name: qm-oci-hooks
Version: %{version}
Release: 1%{?dist}
Summary: OCI hooks for QM containers
License: GPL-2.0-only
URL: https://github.com/containers/qm
Source0: %{url}/archive/qm-oci-hooks-%{version}.tar.gz
BuildArch: noarch
# Runtime dependencies
Requires: qm >= %{version}
Requires: jq
%description
This subpackage provides OCI hooks for QM containers that enable dynamic
device access and Wayland display server integration. The hooks are installed
both on the host system and inside the QM rootfs to support nested containers.
Included hooks:
- qm-device-manager: Dynamic device mounting based on container annotations
- wayland-client-devices: GPU hardware acceleration for Wayland clients
The hooks are available in two locations:
- Host system: /usr/libexec/oci/hooks.d/ and /usr/share/containers/oci/hooks.d/
- QM rootfs: /usr/lib/qm/rootfs/usr/libexec/oci/hooks.d/ and /usr/lib/qm/rootfs/usr/share/containers/oci/hooks.d/
%prep
%autosetup -Sgit -n qm-oci-hooks-%{version}
%build
# No build required for OCI hooks
%install
# Create OCI hook directories
install -d %{buildroot}%{_libexecdir}/oci/hooks.d
install -d %{buildroot}%{_libexecdir}/oci/lib
install -d %{buildroot}%{_datadir}/containers/oci/hooks.d
# Note: QM rootfs directories (/usr/lib/qm/rootfs/*) are handled by ghost directories in main qm package
# We only need to create the specific directories we're installing into
install -d %{buildroot}%{qm_rootfs_prefix}%{_libexecdir}/oci/hooks.d
install -d %{buildroot}%{qm_rootfs_prefix}%{_libexecdir}/oci/lib
install -d %{buildroot}%{qm_rootfs_prefix}%{_datadir}/containers/oci/hooks.d
# Install QM Device Manager hook
install -m 755 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/qm-device-manager/oci-qm-device-manager \
%{buildroot}%{_libexecdir}/oci/hooks.d/oci-qm-device-manager
install -m 644 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/qm-device-manager/oci-qm-device-manager.json \
%{buildroot}%{_datadir}/containers/oci/hooks.d/oci-qm-device-manager.json
install -m 755 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/qm-device-manager/oci-qm-device-manager \
%{buildroot}%{qm_rootfs_prefix}%{_libexecdir}/oci/hooks.d/oci-qm-device-manager
install -m 644 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/qm-device-manager/oci-qm-device-manager.json \
%{buildroot}%{qm_rootfs_prefix}%{_datadir}/containers/oci/hooks.d/oci-qm-device-manager.json
# Install Wayland Client Devices hook
install -m 755 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/wayland-client-devices/oci-qm-wayland-client-devices \
%{buildroot}%{_libexecdir}/oci/hooks.d/oci-qm-wayland-client-devices
install -m 644 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/wayland-client-devices/oci-qm-wayland-client-devices.json \
%{buildroot}%{_datadir}/containers/oci/hooks.d/oci-qm-wayland-client-devices.json
install -m 755 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/wayland-client-devices/oci-qm-wayland-client-devices \
%{buildroot}%{qm_rootfs_prefix}%{_libexecdir}/oci/hooks.d/oci-qm-wayland-client-devices
install -m 644 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/wayland-client-devices/oci-qm-wayland-client-devices.json \
%{buildroot}%{qm_rootfs_prefix}%{_datadir}/containers/oci/hooks.d/oci-qm-wayland-client-devices.json
# Install common libraries
install -m 644 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/lib/common.sh \
%{buildroot}%{_libexecdir}/oci/lib/common.sh
install -m 644 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/lib/device-support.sh \
%{buildroot}%{_libexecdir}/oci/lib/device-support.sh
install -m 644 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/lib/common.sh \
%{buildroot}%{qm_rootfs_prefix}%{_libexecdir}/oci/lib/common.sh
install -m 644 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/lib/device-support.sh \
%{buildroot}%{qm_rootfs_prefix}%{_libexecdir}/oci/lib/device-support.sh
# Create documentation directory and install component-specific README files with unique names
install -d %{buildroot}%{_docdir}/qm-oci-hooks
install -m 644 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/qm-device-manager/README.md \
%{buildroot}%{_docdir}/qm-oci-hooks/README-qm-device-manager.md
install -m 644 %{_builddir}/qm-oci-hooks-%{version}/oci-hooks/wayland-client-devices/README.md \
%{buildroot}%{_docdir}/qm-oci-hooks/README-wayland-client-devices.md
%files
%license LICENSE
%doc CODE-OF-CONDUCT.md README.md SECURITY.md
%{_docdir}/qm-oci-hooks/README-qm-device-manager.md
%{_docdir}/qm-oci-hooks/README-wayland-client-devices.md
# OCI hook executables and libraries (host system)
%dir %{_libexecdir}/oci
%dir %{_libexecdir}/oci/hooks.d
%dir %{_libexecdir}/oci/lib
%{_libexecdir}/oci/hooks.d/oci-qm-device-manager
%{_libexecdir}/oci/hooks.d/oci-qm-wayland-client-devices
%{_libexecdir}/oci/lib/common.sh
%{_libexecdir}/oci/lib/device-support.sh
# OCI hook configurations (host system)
%dir %{_datadir}/containers/oci
%dir %{_datadir}/containers/oci/hooks.d
%{_datadir}/containers/oci/hooks.d/oci-qm-device-manager.json
%{_datadir}/containers/oci/hooks.d/oci-qm-wayland-client-devices.json
# OCI hook executables and libraries (QM rootfs for nested containers)
%{qm_rootfs_prefix}%{_libexecdir}/oci/hooks.d/oci-qm-device-manager
%{qm_rootfs_prefix}%{_libexecdir}/oci/hooks.d/oci-qm-wayland-client-devices
%{qm_rootfs_prefix}%{_libexecdir}/oci/lib/common.sh
%{qm_rootfs_prefix}%{_libexecdir}/oci/lib/device-support.sh
# OCI hook configurations (QM rootfs for nested containers)
%{qm_rootfs_prefix}%{_datadir}/containers/oci/hooks.d/oci-qm-device-manager.json
%{qm_rootfs_prefix}%{_datadir}/containers/oci/hooks.d/oci-qm-wayland-client-devices.json
%changelog
* Fri Jul 21 2023 RH Container Bot <rhcontainerbot@fedoraproject.org>
- Initial release of consolidated QM OCI hooks package

Some files were not shown because too many files have changed in this diff Show More