From 1a9ca84eed1233b8544b1c494590faee03bb5790 Mon Sep 17 00:00:00 2001 From: Alexander Livenets Date: Fri, 10 Apr 2020 00:40:30 +0200 Subject: [PATCH 1/3] libsoftwarecontainer: Define unconfined AppArmor profile for containers Signed-off-by: Alexander Livenets --- libsoftwarecontainer/softwarecontainer.conf.in | 2 ++ 1 file changed, 2 insertions(+) diff --git a/libsoftwarecontainer/softwarecontainer.conf.in b/libsoftwarecontainer/softwarecontainer.conf.in index 539594498..accb5a76f 100644 --- a/libsoftwarecontainer/softwarecontainer.conf.in +++ b/libsoftwarecontainer/softwarecontainer.conf.in @@ -21,3 +21,5 @@ lxc.mount.entry = /lib lib none ro,bind 0 0 # These are optional, as they may not exist in the host. If they exist # they will be bind mounted from host to container. lxc.mount.entry = /lib64 lib64 none ro,bind,optional 0 0 + +lxc.apparmor.profile = unconfined From 5f3aa606ade45ce563c3645404152c8804bdbe64 Mon Sep 17 00:00:00 2001 From: Alexander Livenets Date: Fri, 10 Apr 2020 00:42:19 +0200 Subject: [PATCH 2/3] wayland: Fix WAYLAND_DISPLAY variable processing Use default socket name `wayland-0` if variable is not set Signed-off-by: Alexander Livenets --- .../softwarecontainerlib_componenttest.cpp | 10 +++++++++- .../src/gateway/waylandgateway.cpp | 15 +++++++++------ 2 files changed, 18 insertions(+), 7 deletions(-) diff --git a/libsoftwarecontainer/component-test/softwarecontainerlib_componenttest.cpp b/libsoftwarecontainer/component-test/softwarecontainerlib_componenttest.cpp index aca07a491..4baab1ffb 100644 --- a/libsoftwarecontainer/component-test/softwarecontainerlib_componenttest.cpp +++ b/libsoftwarecontainer/component-test/softwarecontainerlib_componenttest.cpp @@ -98,7 +98,15 @@ class SoftwareContainerApp : public SoftwareContainerLibTest log_debug() << "Wayland dir : " << waylandDir; - std::string socketPath = buildPath(waylandDir, WaylandGateway::SOCKET_FILE_NAME); + bool hasWaylandSocket = false; + std::string waylandSocketFileName = Glib::getenv(WaylandGateway::WAYLAND_SOCKET_FILE_VARIABLE_NAME, + hasWaylandSocket); + if (!hasWaylandSocket) { + log_error() << "No wayland socket"; + return ERROR; + } + + std::string socketPath = buildPath(waylandDir, waylandSocketFileName); log_debug() << "isSocket : " << socketPath << " " << isSocket(socketPath); if (!isSocket(socketPath)) { diff --git a/libsoftwarecontainer/src/gateway/waylandgateway.cpp b/libsoftwarecontainer/src/gateway/waylandgateway.cpp index 3ee24b972..b0d5862e3 100644 --- a/libsoftwarecontainer/src/gateway/waylandgateway.cpp +++ b/libsoftwarecontainer/src/gateway/waylandgateway.cpp @@ -29,6 +29,8 @@ constexpr const char *WaylandGateway::ENABLED_FIELD; constexpr const char *WaylandGateway::WAYLAND_RUNTIME_DIR_VARIABLE_NAME; constexpr const char *WaylandGateway::WAYLAND_SOCKET_FILE_VARIABLE_NAME; +static constexpr const char *DEFAULT_WAYLAND_SOCKET_FILE_NAME = "wayland-0"; + WaylandGateway::WaylandGateway(std::shared_ptr container) : Gateway(ID, container, true /*this GW is dynamic*/), m_enabled(false), @@ -72,10 +74,10 @@ bool WaylandGateway::activateGateway() return true; } - std::string SOCKET_FILE_NAME = Glib::getenv(WAYLAND_SOCKET_FILE_VARIABLE_NAME); - if (SOCKET_FILE_NAME.empty()) { - log_error() << "Missing Wayland socket file name. " << WAYLAND_SOCKET_FILE_VARIABLE_NAME << " environment variable not set"; - return false; + std::string socketFileName = Glib::getenv(WAYLAND_SOCKET_FILE_VARIABLE_NAME); + if (socketFileName.empty()) { + log_warn() << "Missing Wayland socket file name. " << WAYLAND_SOCKET_FILE_VARIABLE_NAME << " environment variable not set. Using default filename '" << DEFAULT_WAYLAND_SOCKET_FILE_NAME; + socketFileName = DEFAULT_WAYLAND_SOCKET_FILE_NAME; } bool hasWayland = false; @@ -88,8 +90,8 @@ bool WaylandGateway::activateGateway() std::shared_ptr container = getContainer(); log_info() << "enabling Wayland gateway. Socket dir:" << dir; - std::string pathInHost = buildPath(dir, SOCKET_FILE_NAME); - std::string pathInContainer = buildPath("/gateways", SOCKET_FILE_NAME); + std::string pathInHost = buildPath(dir, socketFileName); + std::string pathInContainer = buildPath("/gateways", socketFileName); if (!container->bindMountInContainer(pathInHost, pathInContainer, false)) { log_error() << "Could not bind mount the wayland socket into the container"; @@ -98,6 +100,7 @@ bool WaylandGateway::activateGateway() std::string socketDir = parentPath(pathInContainer); container->setEnvironmentVariable(WAYLAND_RUNTIME_DIR_VARIABLE_NAME, socketDir); + container->setEnvironmentVariable(WAYLAND_SOCKET_FILE_VARIABLE_NAME, socketFileName); m_activatedOnce = true; From f5af5a24e2c338ad1a99fff2d0532b33d095cc8f Mon Sep 17 00:00:00 2001 From: Alexander Livenets Date: Fri, 10 Apr 2020 00:46:14 +0200 Subject: [PATCH 3/3] test: Fix service tests Rename cgroup `lxc` directory to `lxc.payload`, as defined in LXC library configuration option `DEFAULT_CGROUP_PATTERN` Increase timeout for coredump test Use EnvironmentHelper clean method in environment variable tests Signed-off-by: Alexander Livenets --- servicetest/cgroups/test_cgroups.py | 10 +++++----- servicetest/coredump/test_coredump.py | 2 +- servicetest/environment/test_environment.py | 9 +++------ servicetest/run-tests.sh | 4 ++-- servicetest/testframework/testhelper.py | 5 +++++ 5 files changed, 16 insertions(+), 14 deletions(-) diff --git a/servicetest/cgroups/test_cgroups.py b/servicetest/cgroups/test_cgroups.py index f57d320ef..27e9e9c79 100644 --- a/servicetest/cgroups/test_cgroups.py +++ b/servicetest/cgroups/test_cgroups.py @@ -202,12 +202,12 @@ def test_memory_cgroup_whitelisting(self): most_permissive_value = 1024 * 1024 time.sleep(0.5) - with open("/sys/fs/cgroup/memory/lxc/" + containerID + "/memory.limit_in_bytes", "r") as fh: + with open("/sys/fs/cgroup/memory/lxc.payload/" + containerID + "/memory.limit_in_bytes", "r") as fh: limit_in_bytes = int(fh.read()) assert limit_in_bytes == most_permissive_value most_permissive_value = 10 * 1024 * 1024 - with open("/sys/fs/cgroup/memory/lxc/" + containerID + "/memory.memsw.limit_in_bytes", "r") as fh: + with open("/sys/fs/cgroup/memory/lxc.payload/" + containerID + "/memory.memsw.limit_in_bytes", "r") as fh: memsw_limit = int(fh.read()) assert memsw_limit == most_permissive_value @@ -230,7 +230,7 @@ def test_netcls_cgroup_set(self): sc.set_capabilities(["test.cap.netcls"]) time.sleep(0.5) - with open("/sys/fs/cgroup/net_cls/lxc/" + containerID + "/net_cls.classid", "r") as fh: + with open("/sys/fs/cgroup/net_cls/lxc.payload/" + containerID + "/net_cls.classid", "r") as fh: value = int(fh.read()) assert value == int(TEST_NETCLS_VALUE, base=16) finally: @@ -248,7 +248,7 @@ def test_cpu_shares_cgroup_set(self): sc.set_capabilities(["test.cap.cpu.shares.threshold"]) time.sleep(0.5) - with open("/sys/fs/cgroup/cpu/lxc/" + containerID + "/cpu.shares", "r") as fh: + with open("/sys/fs/cgroup/cpu/lxc.payload/" + containerID + "/cpu.shares", "r") as fh: value = int(fh.read()) assert value == int(CPU_SHARES_LOW_VALUE) finally: @@ -266,7 +266,7 @@ def test_cpu_shares_cgroup_whitelisting(self): most_permissive_value = int(CPU_SHARES_WHITELISTING_VALUE) time.sleep(0.5) - with open("/sys/fs/cgroup/cpu/lxc/" + containerID + "/cpu.shares", "r") as fh: + with open("/sys/fs/cgroup/cpu/lxc.payload/" + containerID + "/cpu.shares", "r") as fh: value = int(fh.read()) assert value == most_permissive_value diff --git a/servicetest/coredump/test_coredump.py b/servicetest/coredump/test_coredump.py index d363e9efd..9c821b3c1 100644 --- a/servicetest/coredump/test_coredump.py +++ b/servicetest/coredump/test_coredump.py @@ -149,7 +149,7 @@ def test_core_is_dumped(self, core_pattern): ) # Let the helper run a little - time.sleep(0.1) + time.sleep(0.5) # Check that a core was dumped, meaning there are more files in the core dump dir now coreFiles = os.listdir(coredump_path()) diff --git a/servicetest/environment/test_environment.py b/servicetest/environment/test_environment.py index 4a35be94a..3d5958196 100644 --- a/servicetest/environment/test_environment.py +++ b/servicetest/environment/test_environment.py @@ -65,12 +65,9 @@ def mounted_path_in_host(): def clear_env_files(scope="function"): """ Removes the files used by the helper to avoid having false positives from previous test runs. - - TODO: Should this be a method on the helper? """ - file_path = os.path.join(TESTOUTPUT_DIR, EnvironmentHelper.ENV_VARS_FILE_NAME) - if os.path.exists(file_path): - os.remove(file_path) + helper = EnvironmentHelper(TESTOUTPUT_DIR) + helper.clean() ##### Globals for setup and configuration of SC ##### @@ -456,7 +453,7 @@ def test_caps_for_one_container_does_not_affect_another_container(self): assert my_env_var_1 == "1" and my_env_var_2 == "2" # Make sure we remove the env file so that we don't get a cached version for sc2 - clear_env_files() + helper.clean() # This cap should set only one env var in the container sc2.set_capabilities(["environment.test.cap.7"]) diff --git a/servicetest/run-tests.sh b/servicetest/run-tests.sh index 4ecab807d..bf009daea 100755 --- a/servicetest/run-tests.sh +++ b/servicetest/run-tests.sh @@ -25,5 +25,5 @@ fi # cd to the directory of this script. cd "$(dirname "$0")" -py.test-3 -v -k "not agent" --junit-xml=servicetest_result.xml -py.test-3 -v -k "agent" --junit-xml=agent_servicetest_result.xml +py.test -v -k "not agent" --junit-xml=servicetest_result.xml +py.test -v -k "agent" --junit-xml=agent_servicetest_result.xml diff --git a/servicetest/testframework/testhelper.py b/servicetest/testframework/testhelper.py index ff21c09f7..aefbcccdf 100644 --- a/servicetest/testframework/testhelper.py +++ b/servicetest/testframework/testhelper.py @@ -147,6 +147,11 @@ def write_result(self, data): with open(self._base_path + "/" + self.__file_name(), "w") as fh: fh.write(json.dumps(data.data)) + def clean(self): + file_path = os.path.join(self._base_path, self.ENV_VARS_FILE_NAME) + if os.path.exists(file_path): + os.remove(file_path) + def get_env_vars(self): LOG("Getting all env vars") all_vars = os.environ