From fecfd03a1a0edc792e0fb7d72a25fc9aa12f3909 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pavel=20Czern=C3=BD?= Date: Tue, 26 Jul 2022 09:18:08 +0200 Subject: [PATCH] M #-: Restricted dirs for CONTEXT/FILES (#2243) * M #-: Restricted dirs for CONTEXT/FILES * M #-: Fix opennebula_configuration.xsd --- share/doc/xsd/opennebula_configuration.xsd | 2 + src/template/OpenNebulaTemplate.cc | 2 + src/vm/VirtualMachineContext.cc | 60 ++++++++++++++++++++++ src/vmm/VirtualMachineManager.cc | 3 ++ 4 files changed, 67 insertions(+) diff --git a/share/doc/xsd/opennebula_configuration.xsd b/share/doc/xsd/opennebula_configuration.xsd index ab05c987b1..44ce92ea81 100644 --- a/share/doc/xsd/opennebula_configuration.xsd +++ b/share/doc/xsd/opennebula_configuration.xsd @@ -28,6 +28,8 @@ + + diff --git a/src/template/OpenNebulaTemplate.cc b/src/template/OpenNebulaTemplate.cc index be77ebc152..144187a58c 100644 --- a/src/template/OpenNebulaTemplate.cc +++ b/src/template/OpenNebulaTemplate.cc @@ -399,6 +399,8 @@ void OpenNebulaTemplate::set_conf_default() set_conf_single("HOST_ENCRYPTED_ATTR", "NSX_PASSWORD"); set_conf_single("HOST_ENCRYPTED_ATTR", "ONE_PASSWORD"); set_conf_single("SHOWBACK_ONLY_RUNNING", "NO"); + set_conf_single("CONTEXT_RESTRICTED_DIRS", "/etc"); + set_conf_single("CONTEXT_SAFE_DIRS", ""); //DB CONFIGURATION vvalue.insert(make_pair("BACKEND","sqlite")); diff --git a/src/vm/VirtualMachineContext.cc b/src/vm/VirtualMachineContext.cc index def2b9ac7b..74ffbcacdb 100644 --- a/src/vm/VirtualMachineContext.cc +++ b/src/vm/VirtualMachineContext.cc @@ -70,6 +70,39 @@ const std::vector NETWORK6_CONTEXT = { {"EXTERNAL", "EXTERNAL", "", false}, }; +bool is_restricted(const string& path, + const set& restricted, + const set& safe) +{ + auto canonical_c = realpath(path.c_str(), nullptr); + + if (canonical_c == nullptr) + { + return false; + } + + string canonical_str(canonical_c); + free(canonical_c); + + for (auto& s : safe) + { + if (canonical_str.find(s) == 0) + { + return false; + } + } + + for (auto& r : restricted) + { + if (canonical_str.find(r) == 0) + { + return true; + } + } + + return false; +} + /* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */ /* CONTEXT - Public Interface */ @@ -129,6 +162,33 @@ int VirtualMachine::generate_context(string &files, int &disk_id, } files = context->vector_value("FILES"); + + auto& nd = Nebula::instance(); + string restricted_dirs, safe_dirs; + nd.get_configuration_attribute("CONTEXT_RESTRICTED_DIRS", restricted_dirs); + nd.get_configuration_attribute("CONTEXT_SAFE_DIRS", safe_dirs); + + set restricted, safe; + + one_util::split_unique(restricted_dirs, ' ', restricted); + one_util::split_unique(safe_dirs, ' ', safe); + + set files_set; + one_util::split_unique(files, ' ', files_set); + for (auto& f : files_set) + { + if (is_restricted(f, restricted, safe)) + { + string error = "CONTEXT/FILES cannot use " + f + + ", it's in restricted directories"; + + log("VM", Log::ERROR, error); + set_template_error_message(error); + + return -1; + } + } + files_ds = context->vector_value("FILES_DS"); if (!files_ds.empty()) diff --git a/src/vmm/VirtualMachineManager.cc b/src/vmm/VirtualMachineManager.cc index 961c1209eb..e1b9774e01 100644 --- a/src/vmm/VirtualMachineManager.cc +++ b/src/vmm/VirtualMachineManager.cc @@ -333,6 +333,9 @@ static int do_context_command(VirtualMachine * vm, const string& password, if ( rc == -1 ) { + auto vmpool = Nebula::instance().get_vmpool(); + vmpool->update(vm); + return -1; } else if ( rc == 1 )