iSulad/0120-nri-add-convert-and-utils-impl-for-nri.patch

2255 lines
75 KiB
Diff
Raw Permalink Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

From c0d4b523c24e88b8c70cd3b121a46b7b3c841c17 Mon Sep 17 00:00:00 2001
From: zhongtao <zhongtao17@huawei.com>
Date: Tue, 13 Aug 2024 20:33:28 +0800
Subject: [PATCH 120/149] [nri] add convert and utils impl for nri
Signed-off-by: zhongtao <zhongtao17@huawei.com>
---
src/daemon/common/nri/nri_convert.cc | 539 ++++++++++++++++++++++++
src/daemon/common/nri/nri_convert.h | 9 +-
src/daemon/common/nri/nri_spec.c | 602 +++++++++++++++++++++++++++
src/daemon/common/nri/nri_utils.c | 520 +++++++++++++++++++++++
src/daemon/common/nri/nri_utils.h | 5 +-
src/daemon/config/isulad_config.c | 178 ++++++++
src/daemon/modules/api/specs_api.h | 5 +
src/daemon/modules/spec/specs.c | 32 +-
src/daemon/nri/nri_adaption.h | 46 +-
src/daemon/nri/nri_helpers.cc | 93 +++++
src/daemon/nri/nri_helpers.h | 2 +-
src/utils/cpputils/transform.cc | 2 +-
12 files changed, 2002 insertions(+), 31 deletions(-)
create mode 100644 src/daemon/common/nri/nri_convert.cc
create mode 100644 src/daemon/common/nri/nri_spec.c
create mode 100644 src/daemon/common/nri/nri_utils.c
create mode 100644 src/daemon/nri/nri_helpers.cc
diff --git a/src/daemon/common/nri/nri_convert.cc b/src/daemon/common/nri/nri_convert.cc
new file mode 100644
index 00000000..7cce64ec
--- /dev/null
+++ b/src/daemon/common/nri/nri_convert.cc
@@ -0,0 +1,539 @@
+/******************************************************************************
+ * Copyright (c) Huawei Technologies Co., Ltd. 2024. All rights reserved.
+ * iSulad licensed under the Mulan PSL v2.
+ * You can use this software according to the terms and conditions of the Mulan PSL v2.
+ * You may obtain a copy of Mulan PSL v2 at:
+ * http://license.coscl.org.cn/MulanPSL2
+ * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR
+ * PURPOSE.
+ * See the Mulan PSL v2 for more details.
+ * Author: zhongtao
+ * Create: 2024-03-16
+ * Description: provide nri convert functions
+ *********************************************************************************/
+
+#include "nri_convert.h"
+
+#include "container_api.h"
+#include "v1_cri_helpers.h"
+#include "path.h"
+#include "transform.h"
+#include "nri_utils.h"
+
+static int64_t DefaultOOMScoreAdj = 0;
+
+static bool NRILinuxCpuFromCRI(const runtime::v1::LinuxContainerResources &config, nri_linux_cpu &cpu)
+{
+ if (!config.cpuset_cpus().empty()) {
+ cpu.cpus = util_strdup_s(config.cpuset_cpus().c_str());
+ }
+
+ if (!config.cpuset_mems().empty()) {
+ cpu.mems = util_strdup_s(config.cpuset_mems().c_str());
+ }
+
+ cpu.period = (uint64_t *)util_common_calloc_s(sizeof(uint64_t));
+ if (cpu.period == nullptr) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(cpu.period) = config.cpu_period();
+
+ cpu.quota = (int64_t *)util_common_calloc_s(sizeof(int64_t));
+ if (cpu.quota == nullptr) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(cpu.quota) = config.cpu_quota();
+
+ cpu.shares = (uint64_t *)util_common_calloc_s(sizeof(uint64_t));
+ if (cpu.shares == nullptr) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(cpu.shares) = config.cpu_shares();
+
+ // consistent with other container engines,
+ // not obtained cpu.realtime_period & cpu.realtime_runtime
+ return true;
+}
+
+static bool NRILinuxMemoryFromCRI(const runtime::v1::LinuxContainerResources &config, nri_linux_memory &memory)
+{
+ memory.limit = (int64_t *)util_common_calloc_s(sizeof(int64_t));
+ if (memory.limit == nullptr) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(memory.limit) = config.memory_limit_in_bytes();
+
+ // consistent with other container engines,
+ // not obtained other memory info
+
+ return true;
+}
+
+static bool NRIHugePageLimitFromCRI(const runtime::v1::LinuxContainerResources &config, nri_linux_resources &resources)
+{
+ int i;
+ nri_hugepage_limit *tmp = nullptr;
+
+ if (config.hugepage_limits_size() == 0) {
+ return true;
+ }
+
+ resources.hugepage_limits = (nri_hugepage_limit **)util_smart_calloc_s(sizeof(nri_hugepage_limit *),
+ config.hugepage_limits_size());
+ if (resources.hugepage_limits == nullptr) {
+ ERROR("Out of memory");
+ return false;
+ }
+
+ for (i = 0; i < config.hugepage_limits_size(); i++) {
+ tmp = (nri_hugepage_limit *)util_common_calloc_s(sizeof(nri_hugepage_limit));
+ if (tmp == nullptr) {
+ ERROR("Out of memory");
+ return false;
+ }
+ tmp->page_size = util_strdup_s(config.hugepage_limits(i).page_size().c_str());
+ tmp->limit = config.hugepage_limits(i).limit();
+ resources.hugepage_limits[i] = tmp;
+ resources.hugepage_limits_len++;
+ tmp = nullptr;
+ }
+ return true;
+}
+
+static auto NRILinuxResourcesFromCRI(const runtime::v1::LinuxContainerResources &config,
+ nri_linux_resources &resources) -> bool
+{
+ if (!NRILinuxMemoryFromCRI(config, *resources.memory)) {
+ ERROR("Failed to transform memory to nri for container");
+ return false;
+ }
+
+ if (!NRILinuxCpuFromCRI(config, *resources.cpu)) {
+ ERROR("Failed to transform cpu to nri for container");
+ return false;
+ }
+
+ if (!NRIHugePageLimitFromCRI(config, resources)) {
+ ERROR("Failed to transform hugepage limits to nri for container");
+ return false;
+ }
+
+ // resources.blockio_class is not support
+ // resources.rdt_class is not support
+ // They are not standard fields in oci spec
+
+ Errors tmpError;
+
+ resources.unified = Transform::ProtobufMapToJsonMapForString(config.unified(), tmpError);
+ if (resources.unified == nullptr) {
+ ERROR("Failed to transform unified to nri for container : %s", tmpError.GetMessage().c_str());
+ return false;
+ }
+
+ // resources.devices is not set in pod
+
+ return true;
+}
+
+static auto NRILinuxFromCRI(const runtime::v1::LinuxPodSandboxConfig &config, nri_linux_pod_sandbox &linux) -> bool
+{
+ if (!init_nri_linux_resources(&linux.pod_overhead)) {
+ ERROR("Failed to init nri linux overhead resources for pod");
+ return false;
+ }
+ if (!init_nri_linux_resources(&linux.pod_resources)) {
+ ERROR("Failed to init nri linux resources resources for pod");
+ return false;
+ }
+ if (config.has_overhead() && !NRILinuxResourcesFromCRI(config.overhead(), *linux.pod_overhead)) {
+ ERROR("Failed to transform overhead to nri for pod");
+ return false;
+ }
+
+ if (config.has_resources() && !NRILinuxResourcesFromCRI(config.resources(), *linux.pod_resources)) {
+ ERROR("Failed to transform resources to nri for pod");
+ return false;
+ }
+
+ linux.cgroup_parent = util_strdup_s(config.cgroup_parent().c_str());
+
+ // todo: other container engines get linux.cgroups_path/linux.resourses/linux.namespace from spec.linux,
+ // How does isulad get these values from CRI module?
+ return true;
+}
+
+auto PodSandboxToNRI(const std::shared_ptr<const sandbox::Sandbox> &sandbox, nri_pod_sandbox &pod) -> bool
+{
+ container_t *cont = nullptr;
+ Errors tmpError;
+
+ cont = containers_store_get(sandbox->GetName().c_str());
+ if (cont != nullptr) {
+ pod.pid = container_state_get_pid(cont->state);
+ container_unref(cont);
+ }
+
+ pod.id = util_strdup_s(sandbox->GetId().c_str());
+ pod.name = util_strdup_s(sandbox->GetName().c_str());
+ if (sandbox->GetSandboxConfig().has_metadata()) {
+ pod.uid = util_strdup_s(sandbox->GetSandboxConfig().metadata().uid().c_str());
+ pod._namespace = util_strdup_s(sandbox->GetSandboxConfig().metadata().namespace_().c_str());
+ }
+
+
+ pod.labels = Transform::ProtobufMapToJsonMapForString(sandbox->GetSandboxConfig().labels(), tmpError);
+ if (pod.labels == nullptr) {
+ ERROR("Failed to transform labels to nri for pod : %s, : %s", pod.name, tmpError.GetMessage().c_str());
+ return false;
+ }
+
+ pod.annotations = Transform::ProtobufMapToJsonMapForString(sandbox->GetSandboxConfig().annotations(), tmpError);
+ if (pod.annotations == nullptr) {
+ ERROR("Failed to transform annotations to nri for pod : %s, : %s", pod.name, tmpError.GetMessage().c_str());
+ return false;
+ }
+
+ if (sandbox->GetSandboxConfig().has_linux()) {
+ pod.linux = (nri_linux_pod_sandbox *)util_common_calloc_s(sizeof(nri_linux_pod_sandbox));
+ if (pod.linux == nullptr) {
+ ERROR("Out of memory");
+ return false;
+ }
+ if (!NRILinuxFromCRI(sandbox->GetSandboxConfig().linux(), *pod.linux)) {
+ ERROR("Failed to transform linux to nri for pod : %s", pod.name);
+ return false;
+ }
+ }
+
+ pod.runtime_handler = util_strdup_s(sandbox->GetRuntimeHandle().c_str());
+
+ return true;
+}
+
+static auto CRIMountArrToNRI(const runtime::v1::ContainerConfig &containerConfig, nri_container &con) -> bool
+{
+ size_t i, len;
+
+ // get mount from cont
+ len = containerConfig.mounts_size();
+ if (len == 0) {
+ return true;
+ }
+ con.mounts = (nri_mount **)util_smart_calloc_s(sizeof(nri_mount *), len);
+ if (con.mounts == nullptr) {
+ ERROR("Out of memory");
+ return false;
+ }
+
+ nri_mount *tmp = nullptr;
+
+ for (i = 0; i < len; i++) {
+ tmp = (nri_mount *)util_common_calloc_s(sizeof(nri_mount));
+ if (tmp == nullptr) {
+ ERROR("Out of memory");
+ goto error_out;
+ }
+
+ if (containerConfig.mounts()[i].container_path().empty() || containerConfig.mounts()[i].host_path().empty()) {
+ ERROR("Mount path is empty");
+ goto error_out;
+ }
+
+ char path[PATH_MAX] = { 0 };
+ if (!util_clean_path(containerConfig.mounts()[i].container_path().c_str(), path, sizeof(path))) {
+ ERROR("Failed to get clean path for mount src path: %s", containerConfig.mounts()[i].container_path().c_str());
+ goto error_out;
+ }
+
+ tmp->destination = util_strdup_s(path);
+
+ if (!util_clean_path(containerConfig.mounts()[i].host_path().c_str(), path, sizeof(path))) {
+ ERROR("Failed to get clean path for mount src path: %s", containerConfig.mounts()[i].host_path().c_str());
+ goto error_out;
+ }
+ tmp->source = util_strdup_s(path);
+
+ if (util_array_append(&(tmp->options), "rbind") != 0) {
+ ERROR("Failed to append options");
+ goto error_out;
+ }
+
+ if (containerConfig.mounts()[i].propagation() == runtime::v1::PROPAGATION_PRIVATE) {
+ DEBUG("noop, private is default");
+ if (util_array_append(&(tmp->options), "rprivate") != 0) {
+ ERROR("Failed to append options");
+ goto error_out;
+ }
+ } else if (containerConfig.mounts()[i].propagation() == runtime::v1::PROPAGATION_BIDIRECTIONAL) {
+ if (util_array_append(&(tmp->options), "rshared") != 0) {
+ ERROR("Failed to append options");
+ goto error_out;
+ }
+ } else if (containerConfig.mounts()[i].propagation() == runtime::v1::PROPAGATION_HOST_TO_CONTAINER) {
+ if (util_array_append(&(tmp->options), "rslave") != 0) {
+ ERROR("Failed to append options");
+ goto error_out;
+ }
+ } else {
+ WARN("unknown propagation mode for hostPath %s", containerConfig.mounts()[i].host_path().c_str());
+ if (util_array_append(&(tmp->options), "rprivate") != 0) {
+ ERROR("Failed to append options");
+ goto error_out;
+ }
+ }
+
+ if (containerConfig.mounts()[i].readonly()) {
+ if (util_array_append(&(tmp->options), "ro") != 0) {
+ ERROR("Failed to append options");
+ goto error_out;
+ }
+ } else {
+ if (util_array_append(&(tmp->options), "rw") != 0) {
+ ERROR("Failed to append options");
+ goto error_out;
+ }
+ }
+
+ tmp->type = util_strdup_s("bind");
+
+ con.mounts[i] = tmp;
+ tmp = nullptr;
+ con.mounts_len++;
+ }
+ return true;
+
+error_out:
+ free_nri_mount(tmp);
+ return false;
+}
+
+static auto MountPointsElementToNRI(container_config_v2_common_config_mount_points *mp, nri_container &con) -> bool
+{
+ size_t i, len;
+ nri_mount *tmp = nullptr;
+
+ if (mp == nullptr || mp->len == 0) {
+ return true;
+ }
+ len = mp->len;
+
+ con.mounts = (nri_mount **)util_smart_calloc_s(sizeof(nri_mount *), len);
+ if (con.mounts == nullptr) {
+ ERROR("Out of memory");
+ return false;
+ }
+
+ for (i = 0; i < len; i++) {
+ tmp = (nri_mount *)util_common_calloc_s(sizeof(nri_mount));
+ char path[PATH_MAX] = { 0 };
+
+ if (!util_clean_path(mp->values[i]->destination, path, sizeof(path))) {
+ ERROR("Failed to get clean path for mount dest path: %s", mp->values[i]->destination);
+ goto error_out;
+ }
+ tmp->destination = util_strdup_s(path);
+
+ if (!util_clean_path(mp->values[i]->source, path, sizeof(path))) {
+ ERROR("Failed to get clean path for mount src path: %s", mp->values[i]->source);
+ goto error_out;
+ }
+ tmp->source = util_strdup_s(path);
+
+ if (util_array_append(&(tmp->options), "rbind") != 0) {
+ ERROR("Failed to append options");
+ goto error_out;
+ }
+ if (util_array_append(&(tmp->options), mp->values[i]->propagation) != 0) {
+ ERROR("Failed to append options");
+ goto error_out;
+ }
+
+ if (mp->values[i]->rw) {
+ if (util_array_append(&(tmp->options), "rw") != 0) {
+ ERROR("Failed to append options");
+ goto error_out;
+ }
+ } else {
+ if (util_array_append(&(tmp->options), "ro") != 0) {
+ ERROR("Failed to append options");
+ goto error_out;
+ }
+ }
+
+ tmp->type = util_strdup_s("bind");
+ con.mounts[i] = tmp;
+ con.mounts_len++;
+ tmp = nullptr;
+ }
+
+ return true;
+
+error_out:
+ free_nri_mount(tmp);
+ return false;
+}
+
+// container info is incomplete because container in excution is not created
+auto ContainerToNRIByConConfig(const runtime::v1::ContainerConfig &containerConfig, nri_container &con) -> bool
+{
+ // todo: can not get container id and state from containerConfig
+ if (containerConfig.has_metadata() && !containerConfig.metadata().name().empty()) {
+ con.name = util_strdup_s(containerConfig.metadata().name().c_str());
+ }
+
+ Errors tmpError;
+
+ con.labels = Transform::ProtobufMapToJsonMapForString(containerConfig.labels(), tmpError);
+ if (con.labels == nullptr) {
+ ERROR("Failed to transform labels to nri for con : %s, : %s", con.name, tmpError.GetMessage().c_str());
+ return false;
+ }
+
+ con.annotations = Transform::ProtobufMapToJsonMapForString(containerConfig.annotations(), tmpError);
+ if (con.annotations == nullptr) {
+ ERROR("Failed to transform annotations to nri for con : %s, : %s", con.name, tmpError.GetMessage().c_str());
+ return false;
+ }
+
+ con.args = Transform::RepeatedPtrFieldToCharArray(containerConfig.args());
+ if (con.args == nullptr) {
+ ERROR("Failed to transform args to nri for con : %s, : %s", con.name, tmpError.GetMessage().c_str());
+ return false;
+ }
+ con.args_len = containerConfig.args_size();
+
+ auto envVect = CRIHelpersV1::GenerateEnvList(containerConfig.envs());
+ con.env = Transform::StringVectorToCharArray(envVect);
+ if (con.env == nullptr) {
+ ERROR("Failed to transform env to nri for con : %s", con.name);
+ return false;
+ }
+ con.env_len = containerConfig.envs_size();
+
+ if (!CRIMountArrToNRI(containerConfig, con)) {
+ ERROR("Failed to transform mounts to nri for con : %s", con.name);
+ return false;
+ }
+ return true;
+
+ // todo: can not get container hooks and pid from containerConfig
+}
+
+// container info is incomplete because container in excution is not created
+auto ContainerToNRIByID(const std::string &id, nri_container &con) -> bool
+{
+ container_t *cont = nullptr;
+ bool ret = false;
+
+ cont = containers_store_get(id.c_str());
+ if (cont == nullptr || cont->common_config == nullptr) {
+ ERROR("No such container:%s", id.c_str());
+ goto out;
+ }
+
+ con.id = util_strdup_s(id.c_str());
+
+ con.name = util_strdup_s(cont->common_config->name);
+
+ con.labels = (json_map_string_string *)util_common_calloc_s(sizeof(json_map_string_string));
+ if (con.labels == nullptr) {
+ ERROR("Out of memory");
+ goto out;
+ }
+ con.annotations = (json_map_string_string *)util_common_calloc_s(sizeof(json_map_string_string));
+ if (con.annotations == nullptr) {
+ ERROR("Out of memory");
+ goto out;
+ }
+ // state
+ if (dup_json_map_string_string(cont->common_config->config->labels, con.labels) != 0) {
+ ERROR("Failed to copy labels for con: %s", cont->common_config->name);
+ goto out;
+ }
+ if (dup_json_map_string_string(cont->common_config->config->annotations, con.annotations) != 0) {
+ ERROR("Failed to copy labels for con: %s", cont->common_config->name);
+ goto out;
+ }
+
+ con.args = util_copy_array_by_len(cont->common_config->args, cont->common_config->args_len);
+ if (cont->common_config->args_len != 0 && con.args == nullptr) {
+ ERROR("Failed to copy args for con: %s", cont->common_config->name);
+ goto out;
+ }
+ con.args_len = cont->common_config->args_len;
+
+ con.env = util_copy_array_by_len(cont->common_config->config->env, cont->common_config->config->env_len);
+ if (cont->common_config->config->env_len != 0 && con.env == nullptr) {
+ ERROR("Failed to copy env for con: %s", cont->common_config->name);
+ goto out;
+ }
+ con.env_len = cont->common_config->config->env_len;
+
+ if (!MountPointsElementToNRI(cont->common_config->mount_points, con)) {
+ ERROR("Failed to transform mounts to nri for con : %s", con.name);
+ goto out;
+ }
+
+ // todo: can convert hostconfig's hook_spec to nri spec
+
+ con.pid = container_state_get_pid(cont->state);
+ if (con.pid < 0) {
+ ERROR("Container %s pid %d invalid", cont->common_config->name, con.pid);
+ goto out;
+ }
+
+ con.pod_sandbox_id = util_strdup_s(cont->common_config->sandbox_info->id);
+ ret = true;
+
+out:
+ container_unref(cont);
+ return ret;
+}
+
+auto LinuxResourcesFromNRI(const nri_linux_resources *src, runtime::v1::LinuxContainerResources &resources) -> bool
+{
+ if (src == nullptr) {
+ return false;
+ }
+
+ if (src->memory != nullptr) {
+ resources.set_memory_limit_in_bytes(*src->memory->limit);
+ resources.set_oom_score_adj(DefaultOOMScoreAdj);
+ }
+
+ if (src->cpu != nullptr) {
+ if (src->cpu->shares != NULL) {
+ resources.set_cpu_shares(*src->cpu->shares);
+ }
+ if (src->cpu->quota != NULL) {
+ resources.set_cpu_quota(*src->cpu->quota);
+ }
+ if (src->cpu->period != NULL) {
+ resources.set_cpu_period(*src->cpu->period);
+ }
+
+ resources.set_cpuset_cpus(src->cpu->cpus);
+ resources.set_cpuset_mems(src->cpu->mems);
+ }
+
+ if (src->hugepage_limits != nullptr && src->hugepage_limits_len > 0) {
+ for (size_t i = 0; i < src->hugepage_limits_len; i++) {
+ if (src->hugepage_limits[i] != nullptr) {
+ auto limit = resources.add_hugepage_limits();
+ limit->set_page_size(src->hugepage_limits[i]->page_size);
+ limit->set_limit(src->hugepage_limits[i]->limit);
+ }
+ }
+ }
+
+ if (src->unified != nullptr) {
+ Transform::JsonMapToProtobufMapForString(src->unified, *resources.mutable_unified());
+ }
+
+ return true;
+}
\ No newline at end of file
diff --git a/src/daemon/common/nri/nri_convert.h b/src/daemon/common/nri/nri_convert.h
index 883f7c41..c04b14e4 100644
--- a/src/daemon/common/nri/nri_convert.h
+++ b/src/daemon/common/nri/nri_convert.h
@@ -27,10 +27,11 @@
#include "sandbox.h"
#include "api_v1.pb.h"
-auto PodSandboxToNRI(const std::shared_ptr<const sandbox::Sandbox> &sandbox, nri_pod_sandbox *pod) -> bool;
-auto ContainerToNRIByConConfig(const runtime::v1::ContainerConfig &containerConfig, nri_container *con) -> bool;
-auto ContainerToNRIByID(const std::string &id, nri_container *con) -> bool;
-auto PodSandboxesToNRI(const std::vector<std::unique_ptr<sandbox::Sandbox>> &arrs, nri_pod_sandbox **pod, int pod_len) -> bool;
+auto PodSandboxToNRI(const std::shared_ptr<const sandbox::Sandbox> &sandbox, nri_pod_sandbox &pod) -> bool;
+auto ContainerToNRIByConConfig(const runtime::v1::ContainerConfig &containerConfig, nri_container &con) -> bool;
+auto ContainerToNRIByID(const std::string &id, nri_container &con) -> bool;
+auto PodSandboxesToNRI(const std::vector<std::unique_ptr<sandbox::Sandbox>> &arrs, nri_pod_sandbox **pod,
+ int pod_len) -> bool;
auto LinuxResourcesFromNRI(const nri_linux_resources *src, runtime::v1::LinuxContainerResources &resources) -> bool;
#endif // DAEMON_COMMON_NRI_NRI_CONVERT_H
diff --git a/src/daemon/common/nri/nri_spec.c b/src/daemon/common/nri/nri_spec.c
new file mode 100644
index 00000000..855fe3b3
--- /dev/null
+++ b/src/daemon/common/nri/nri_spec.c
@@ -0,0 +1,602 @@
+/******************************************************************************
+ * Copyright (c) Huawei Technologies Co., Ltd. 2024. All rights reserved.
+ * iSulad licensed under the Mulan PSL v2.
+ * You can use this software according to the terms and conditions of the Mulan PSL v2.
+ * You may obtain a copy of Mulan PSL v2 at:
+ * http://license.coscl.org.cn/MulanPSL2
+ * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR
+ * PURPOSE.
+ * See the Mulan PSL v2 for more details.
+ * Author: zhongtao
+ * Create: 2024-07-17
+ * Description: provide nri oci functions
+ *********************************************************************************/
+
+#include "nri_spec.h"
+
+#include <isula_libutils/log.h>
+
+#include "map.h"
+#include "utils.h"
+#include "utils_string.h"
+#include "nri_utils.h"
+#include "specs_api.h"
+#include "sysinfo.h"
+#include "verify.h"
+#include "specs_extend.h"
+
+static defs_hook *nri_hook_to_oci(const nri_hook *h)
+{
+ defs_hook *oci_hook = NULL;
+
+ if (h == NULL) {
+ return NULL;
+ }
+
+ oci_hook = util_common_calloc_s(sizeof(*oci_hook));
+ if (oci_hook == NULL) {
+ ERROR("Out of memory");
+ return NULL;
+ }
+
+ oci_hook->path = util_strdup_s(h->path);
+ if (h->args_len != 0) {
+ oci_hook->args = util_copy_array_by_len(h->args, h->args_len);
+ if (oci_hook->args == NULL) {
+ ERROR("Failed to copy args");
+ goto error_out;
+ }
+ oci_hook->args_len = h->args_len;
+ }
+ if (h->env_len != 0) {
+ oci_hook->env = util_copy_array_by_len(h->env, h->env_len);
+ if (oci_hook->env == NULL) {
+ ERROR("Failed to copy env");
+ goto error_out;
+ }
+ oci_hook->env_len = h->env_len;
+ }
+ if (h->timeout != NULL) {
+ oci_hook->timeout = *(h->timeout);
+ }
+ return oci_hook;
+
+error_out:
+ free_defs_hook(oci_hook);
+ return NULL;
+}
+
+static defs_device *nri_device_to_oci(nri_linux_device *dev)
+{
+ if (dev == NULL) {
+ return NULL;
+ }
+
+ defs_device *oci_dev = util_common_calloc_s(sizeof(defs_device));
+ if (oci_dev == NULL) {
+ ERROR("Out of memory");
+ return NULL;
+ }
+
+ oci_dev->path = util_strdup_s(dev->path);
+ oci_dev->type = util_strdup_s(dev->type);
+ oci_dev->major = dev->major;
+ oci_dev->minor = dev->minor;
+ if (dev->file_mode != NULL) {
+ oci_dev->file_mode = *dev->file_mode;
+ }
+ if (dev->uid != NULL) {
+ oci_dev->uid = *dev->uid;
+ }
+ if (dev->gid != NULL) {
+ oci_dev->gid = *dev->gid;
+ }
+
+ return oci_dev;
+}
+
+static defs_mount *nri_mount_to_oci(nri_mount *mount)
+{
+ if (mount == NULL) {
+ return NULL;
+ }
+
+ defs_mount *oci_mount = util_common_calloc_s(sizeof(defs_mount));
+ if (oci_mount == NULL) {
+ ERROR("Out of memory");
+ return NULL;
+ }
+
+ oci_mount->destination = util_strdup_s(mount->destination);
+ oci_mount->type = util_strdup_s(mount->type);
+ oci_mount->source = util_strdup_s(mount->source);
+ if (mount->options_len != 0) {
+ oci_mount->options = util_copy_array_by_len(mount->options, mount->options_len);
+ if (oci_mount->options == NULL) {
+ ERROR("Failed to copy options");
+ free_defs_mount(oci_mount);
+ return NULL;
+ }
+ oci_mount->options_len = mount->options_len;
+ }
+
+ return oci_mount;
+}
+
+static int nri_adjust_annotation(const nri_container_adjustment *adjust, oci_runtime_spec *oci_spec)
+{
+ int ret = -1;
+ size_t i;
+
+ if (adjust == NULL || adjust->annotations == NULL || adjust->annotations->len == 0) {
+ return 0;
+ }
+
+ if (make_sure_oci_spec_annotations(oci_spec) != 0) {
+ ERROR("Failed to make sure oci spec annotations");
+ return -1;
+ }
+
+ json_map_string_string *cleard = (json_map_string_string *)util_common_calloc_s(sizeof(json_map_string_string));
+ if (cleard == NULL) {
+ ERROR("Out of memory");
+ return -1;
+ }
+
+ map_t *del = map_new(MAP_STR_STR, MAP_DEFAULT_CMP_FUNC, MAP_DEFAULT_FREE_FUNC);
+ if (del == NULL) {
+ ERROR("Out of memory");
+ goto free_out;
+ }
+
+ for (i = 0; i < adjust->annotations->len; i++) {
+ __isula_auto_free char *out = NULL;
+ if (is_marked_for_removal(adjust->annotations->keys[i], &out)) {
+ if (!map_insert(del, out, "")) {
+ ERROR("Failed to insert del map");
+ goto free_out;
+ }
+ continue;
+ }
+ if (append_json_map_string_string(cleard, adjust->annotations->keys[i],
+ adjust->annotations->values[i]) != 0) {
+ ERROR("Failed to append annotation");
+ goto free_out;
+ }
+ }
+
+ for (i = 0; i < oci_spec->annotations->len; i++) {
+ if (map_search(del, oci_spec->annotations->keys[i]) != NULL) {
+ continue;
+ }
+ append_json_map_string_string(cleard, oci_spec->annotations->keys[i],
+ oci_spec->annotations->values[i]);
+ }
+
+ free_json_map_string_string(oci_spec->annotations);
+ oci_spec->annotations = cleard;
+ ret = 0;
+
+free_out:
+ free_json_map_string_string(cleard);
+ map_free(del);
+ return ret;
+}
+
+static void nri_key_value_map_kvfree(void *key, void *value)
+{
+ free(key);
+
+ // no need to free nri_key_value
+ // nri_key_value *value will be free in nri_container_adjustment *adjust
+}
+
+
+static int nri_adjust_env(const nri_container_adjustment *adjust, oci_runtime_spec *oci_spec)
+{
+ int ret = -1;
+ size_t i;
+ char **old_env = NULL;
+ size_t old_env_len = 0;
+ __isula_auto_array_t char **adjust_env = NULL;
+ size_t adjust_env_len = 0;
+
+ if (adjust->env == NULL || adjust->env_len == 0) {
+ return 0;
+ }
+
+ map_t *mod = map_new(MAP_STR_PTR, MAP_DEFAULT_CMP_FUNC, nri_key_value_map_kvfree);
+ if (mod == NULL) {
+ ERROR("Out of memory");
+ goto free_out;
+ }
+
+ for (i = 0; i < adjust->env_len; i++) {
+ nri_key_value *e = adjust->env[i];
+ char *out = NULL;
+ (void)is_marked_for_removal(e->key, &out);
+
+ if (!map_insert(mod, out, e) == false) {
+ ERROR("Failed to insert mod map");
+ goto free_out;
+ }
+ }
+
+ if (map_size(mod) <= 0 || oci_spec == NULL || oci_spec->process == NULL) {
+ ret = 0;
+ goto free_out;
+ }
+
+ // modify existing environment
+ old_env = oci_spec->process->env;
+ old_env_len = oci_spec->process->env_len;
+ oci_spec->process->env = NULL;
+ oci_spec->process->env_len = 0;
+
+ for (i = 0; i < old_env_len; i++) {
+ __isula_auto_array_t char **envArr = util_string_split_n(old_env[i], '=', 2);
+ if (envArr == NULL) {
+ continue;
+ }
+
+ nri_key_value *target = map_search(mod, envArr[0]);
+ if (target != NULL) {
+ __isula_auto_free char *out = NULL;
+ if (!is_marked_for_removal(envArr[0], &out)) {
+ // If not marked for removal, append modified value
+ __isula_auto_free char *tmp_str = util_string_append(target->key, "=");
+ __isula_auto_free char *final_str = util_string_append(tmp_str, target->value);
+
+ if (util_array_append(&adjust_env, final_str) != 0) {
+ ERROR("Failed to append env");
+ goto free_out;
+ }
+ adjust_env_len++;
+ continue;
+ }
+ }
+ // If not found in mod map, append original value
+ if (util_array_append(&adjust_env, old_env[i]) != 0) {
+ ERROR("Failed to append env");
+ goto free_out;
+ }
+ adjust_env_len++;
+ }
+
+ ret = 0;
+free_out:
+ if (merge_env(oci_spec, (const char **)adjust_env, adjust_env_len) != 0) {
+ ERROR("Failed to merge env");
+ goto free_out;
+ }
+ for (i = 0; i < old_env_len; i++) {
+ free(old_env[i]);
+ }
+ free(old_env);
+ map_free(mod);
+ return ret;
+}
+
+static int nri_adjust_hooks(const nri_container_adjustment *adjust, oci_runtime_spec *oci_spec)
+{
+ if (adjust->hooks == NULL) {
+ return 0;
+ }
+
+ size_t i;
+ int ret = 0;
+
+ if (make_sure_oci_spec_hooks(oci_spec) != 0) {
+ ERROR("Failed to make sure oci spec hooks");
+ return -1;
+ }
+
+ // todo: change to macro definition function call
+ for (i = 0; i < adjust->hooks->prestart_len; i++) {
+ defs_hook *oci_hook = nri_hook_to_oci(adjust->hooks->prestart[i]);
+ ret = spec_add_prestart_hook(oci_spec, oci_hook);
+ if (ret != 0) {
+ ERROR("Failed add hook %s", adjust->hooks->prestart[i]->path);
+ free_defs_hook(oci_hook);
+ return -1;
+ }
+ }
+
+ for (i = 0; i < adjust->hooks->poststart_len; i++) {
+ defs_hook *oci_hook = nri_hook_to_oci(adjust->hooks->poststart[i]);
+ ret = spec_add_poststart_hook(oci_spec, oci_hook);
+ if (ret != 0) {
+ ERROR("Failed add hook %s", adjust->hooks->poststart[i]->path);
+ free_defs_hook(oci_hook);
+ return -1;
+ }
+ }
+
+ for (i = 0; i < adjust->hooks->poststop_len; i++) {
+ defs_hook *oci_hook = nri_hook_to_oci(adjust->hooks->poststop[i]);
+ ret = spec_add_poststop_hook(oci_spec, oci_hook);
+ if (ret != 0) {
+ ERROR("Failed add hook %s", adjust->hooks->poststop[i]->path);
+ free_defs_hook(oci_hook);
+ return -1;
+ }
+ }
+ /*
+ * The OCI being used by the iSulad not supportes
+ * createRuntime/createContainer/startContainer currently.
+ */
+
+ return ret;
+}
+
+static int nri_adjust_devices(const nri_container_adjustment *adjust, oci_runtime_spec *oci_spec)
+{
+ if (adjust->linux == NULL || adjust->linux->devices == NULL || adjust->linux->devices_len == 0) {
+ return 0;
+ }
+
+ size_t i;
+
+ for (i = 0; i < adjust->linux->devices_len; i++) {
+ nri_linux_device *dev = adjust->linux->devices[i];
+ if (spec_add_device(oci_spec, nri_device_to_oci(dev)) != 0) {
+ ERROR("Failed to add device %s", dev->path);
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+static int nri_adjust_cgroup_path(const nri_container_adjustment *adjust, oci_runtime_spec *oci_spec)
+{
+ if (adjust->linux == NULL || adjust->linux->cgroups_path == NULL) {
+ return 0;
+ }
+
+ free(oci_spec->linux->cgroups_path);
+ oci_spec->linux->cgroups_path = util_strdup_s(adjust->linux->cgroups_path);
+
+ return 0;
+}
+
+static void nri_adjust_cpu_memory(nri_linux_resources *resource, oci_runtime_spec *oci_spec)
+{
+ if (resource->cpu == NULL) {
+ return;
+ }
+ if (make_sure_oci_spec_linux_resources_cpu(oci_spec) != 0) {
+ ERROR("Failed to make sure oci spec linux resources cpu");
+ return;
+ }
+ if (resource->cpu->shares != NULL) {
+ oci_spec->linux->resources->cpu->shares = *resource->cpu->shares;
+ }
+ if (resource->cpu->quota != NULL) {
+ oci_spec->linux->resources->cpu->quota = *resource->cpu->quota;
+ }
+ if (resource->cpu->period != NULL) {
+ oci_spec->linux->resources->cpu->period = *resource->cpu->period;
+ }
+ if (resource->cpu->realtime_runtime != NULL) {
+ oci_spec->linux->resources->cpu->realtime_runtime = *resource->cpu->realtime_runtime;
+ }
+ if (resource->cpu->realtime_period != NULL) {
+ oci_spec->linux->resources->cpu->realtime_period = *resource->cpu->realtime_period;
+ }
+}
+
+static void nri_adjust_memory_resource(nri_linux_resources *resource, oci_runtime_spec *oci_spec)
+{
+ if (resource->memory == NULL) {
+ return;
+ }
+
+ if (make_sure_oci_spec_linux_resources_mem(oci_spec) != 0) {
+ ERROR("Failed to make sure oci spec linux resources memory");
+ return;
+ }
+ if (resource->memory->limit != NULL) {
+ oci_spec->linux->resources->memory->limit = *resource->memory->limit;
+ }
+ if (resource->memory->reservation != NULL) {
+ oci_spec->linux->resources->memory->reservation = *resource->memory->reservation;
+ }
+ if (resource->memory->swap != NULL) {
+ oci_spec->linux->resources->memory->swap = *resource->memory->swap;
+ }
+ if (resource->memory->kernel != NULL) {
+ oci_spec->linux->resources->memory->kernel = *resource->memory->kernel;
+ }
+ if (resource->memory->kernel_tcp != NULL) {
+ oci_spec->linux->resources->memory->kernel_tcp = *resource->memory->kernel_tcp;
+ }
+ if (resource->memory->swappiness != NULL) {
+ oci_spec->linux->resources->memory->swappiness = *resource->memory->swappiness;
+ }
+ if (resource->memory->disable_oom_killer != NULL) {
+ oci_spec->linux->resources->memory->disable_oom_killer = *resource->memory->disable_oom_killer;
+ }
+}
+
+static int nri_adjust_hugepage_resource(nri_linux_resources *resource, oci_runtime_spec *oci_spec)
+{
+ size_t i;
+ if (resource->hugepage_limits != NULL) {
+ for (i = 0; i < resource->hugepage_limits_len; i++) {
+ nri_hugepage_limit *limit = resource->hugepage_limits[i];
+ if (limit->page_size != NULL) {
+ if (spec_add_linux_resources_hugepage_limit(oci_spec, limit->page_size, limit->limit) != 0) {
+ ERROR("Failed to add hugepage limit");
+ return -1;
+ }
+ }
+ }
+ }
+ return 0;
+}
+
+static int nri_adjust_unified_resource(nri_linux_resources *resource, oci_runtime_spec *oci_spec)
+{
+ size_t i;
+ if (resource->unified != NULL) {
+ for (i = 0; i < resource->unified->len; i++) {
+ if (append_json_map_string_string(oci_spec->linux->resources->unified, resource->unified->keys[i],
+ resource->unified->values[i]) != 0) {
+ ERROR("Failed to append unified resource");
+ return -1;
+ }
+ }
+ }
+ return 0;
+}
+
+static int nri_adjust_resources(const nri_container_adjustment *adjust, oci_runtime_spec *oci_spec)
+{
+ if (adjust->linux == NULL || adjust->linux->resources == NULL) {
+ return 0;
+ }
+
+ nri_linux_resources *resource = adjust->linux->resources;
+
+ nri_adjust_memory_resource(resource, oci_spec);
+ nri_adjust_cpu_memory(resource, oci_spec);
+
+ if (nri_adjust_hugepage_resource(resource, oci_spec) != 0) {
+ ERROR("Failed to adjust hugepage resource");
+ return -1;
+ }
+
+ if (nri_adjust_unified_resource(resource, oci_spec) != 0) {
+ ERROR("Failed to adjust unified resource");
+ return -1;
+ }
+
+ return 0;
+}
+
+static int nri_adjust_mounts(const nri_container_adjustment *adjust, oci_runtime_spec *oci_spec)
+{
+ if (adjust->mounts == NULL || adjust->mounts_len == 0) {
+ return 0;
+ }
+
+ size_t i;
+ for (i = 0; i < adjust->mounts_len; i++) {
+ nri_mount *mount = adjust->mounts[i];
+ defs_mount *oci_mount = nri_mount_to_oci(mount);
+ if (oci_mount == NULL) {
+ ERROR("Failed to convert nri mount to oci mount");
+ return -1;
+ }
+ if (spec_add_mount(oci_spec, oci_mount) != 0) {
+ ERROR("Failed to add mount");
+ free_defs_mount(oci_mount);
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+static int nri_adjust_rlimit(const nri_container_adjustment *adjust, oci_runtime_spec *oci_spec)
+{
+ if (adjust->rlimits == NULL || adjust->rlimits_len == 0) {
+ return 0;
+ }
+
+ size_t i;
+ for (i = 0; i < adjust->rlimits_len; i++) {
+ nri_posix_rlimit *rlimit = adjust->rlimits[i];
+ if (rlimit->type == NULL) {
+ ERROR("Invalid rlimit type");
+ return -1;
+ }
+ if (spec_add_linux_resources_rlimit(oci_spec, rlimit->type, rlimit->soft, rlimit->hard) != 0) {
+ ERROR("Failed to add rlimit");
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+// todo: we do not support it blockio_class
+static int nri_adjust_blockio_class(const nri_container_adjustment *adjust, oci_runtime_spec *oci_spec)
+{
+ if (adjust->linux == NULL || adjust->linux->resources->blockio_class == NULL) {
+ return 0;
+ }
+
+ return 0;
+}
+
+int nri_adjust_oci_spec(const nri_container_adjustment *adjust, oci_runtime_spec *oci_spec)
+{
+ if (oci_spec == NULL || adjust == NULL) {
+ ERROR("Invalid input arguments");
+ return -1;
+ }
+
+ if (nri_adjust_annotation(adjust, oci_spec) != 0) {
+ ERROR("Failed to do nri adjust annotation in oci spec");
+ return -1;
+ }
+
+ if (nri_adjust_env(adjust, oci_spec) != 0) {
+ ERROR("Failed to do nri adjust env in oci spec");
+ return -1;
+ }
+
+ if (nri_adjust_hooks(adjust, oci_spec) != 0) {
+ ERROR("Failed to do nri adjust hooks in oci spec");
+ return -1;
+ }
+
+ if (nri_adjust_devices(adjust, oci_spec) != 0) {
+ ERROR("Failed to do nri adjust devices in oci spec");
+ return -1;
+ }
+
+ if (nri_adjust_cgroup_path(adjust, oci_spec) != 0) {
+ ERROR("Failed to do nri adjust cgroup path in oci spec");
+ return -1;
+ }
+
+ if (nri_adjust_resources(adjust, oci_spec) != 0) {
+ ERROR("Failed to do nri adjust resources in oci spec");
+ return -1;
+ }
+
+ if (nri_adjust_blockio_class(adjust, oci_spec) != 0) {
+ ERROR("Failed to do nri adjust blockio class in oci spec");
+ return -1;
+ }
+
+ // iSuald is not support IntelRdt
+ if (nri_adjust_mounts(adjust, oci_spec) != 0) {
+ ERROR("Failed to do nri adjust mount in oci spec");
+ return -1;
+ }
+
+ if (nri_adjust_rlimit(adjust, oci_spec) != 0) {
+ ERROR("Failed to do nri adjust rlimit in oci spec");
+ return -1;
+ }
+
+ __isula_auto_sysinfo_t sysinfo_t *sysinfo = NULL;
+
+ sysinfo = get_sys_info(true);
+ if (sysinfo == NULL) {
+ ERROR("Failed to get system info");
+ return -1;
+ }
+
+ if (verify_container_settings(oci_spec, sysinfo) != 0) {
+ ERROR("Failed to verify oci runtime spec settings after adjust by nri");
+ return -1;
+ }
+
+ return 0;
+}
\ No newline at end of file
diff --git a/src/daemon/common/nri/nri_utils.c b/src/daemon/common/nri/nri_utils.c
new file mode 100644
index 00000000..51054e32
--- /dev/null
+++ b/src/daemon/common/nri/nri_utils.c
@@ -0,0 +1,520 @@
+/******************************************************************************
+ * Copyright (c) Huawei Technologies Co., Ltd. 2024. All rights reserved.
+ * iSulad licensed under the Mulan PSL v2.
+ * You can use this software according to the terms and conditions of the Mulan PSL v2.
+ * You may obtain a copy of Mulan PSL v2 at:
+ * http://license.coscl.org.cn/MulanPSL2
+ * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR
+ * PURPOSE.
+ * See the Mulan PSL v2 for more details.
+ * Author: zhongtao
+ * Create: 2024-07-17
+ * Description: provide nri utils functions
+ *********************************************************************************/
+
+#include "nri_utils.h"
+
+#include <isula_libutils/log.h>
+
+#include "utils.h"
+
+static bool copy_nri_hugepage_limit(const nri_hugepage_limit* src, nri_hugepage_limit** dest)
+{
+ if (src == NULL || dest == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+
+ *dest = (nri_hugepage_limit *)util_common_calloc_s(sizeof(nri_hugepage_limit));
+ if (*dest == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+
+ (*dest)->limit = src->limit;
+ (*dest)->page_size = util_strdup_s(src->page_size);
+ return true;
+}
+
+static bool copy_nri_hook(const nri_hook *src, nri_hook **dest)
+{
+ if (src == NULL || dest == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+
+ *dest = (nri_hook *)util_common_calloc_s(sizeof(nri_hook));
+ if (dest == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ (*dest)->args = util_copy_array_by_len(src->args, src->args_len);
+ (*dest)->args_len = src->args_len;
+ (*dest)->env = util_copy_array_by_len(src->env, src->env_len);
+ (*dest)->env_len = src->env_len;
+ (*dest)->path = util_strdup_s(src->path);
+ return true;
+}
+
+static bool copy_nri_linux_device_cgroup(const nri_linux_device_cgroup *src, nri_linux_device_cgroup **dest)
+{
+ if (src == NULL || dest == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+
+ *dest = (nri_linux_device_cgroup *)util_common_calloc_s(sizeof(nri_linux_device_cgroup));
+ if (dest == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ (*dest)->allow = src->allow;
+ (*dest)->type = util_strdup_s(src->type);
+ (*dest)->major = (int64_t *)util_common_calloc_s(sizeof(int64_t));
+ if ((*dest)->major == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ (*dest)->minor = (int64_t *)util_common_calloc_s(sizeof(int64_t));
+ if ((*dest)->minor == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ (*dest)->access = util_strdup_s(src->access);
+ return true;
+}
+
+static bool copy_nri_linux_cpu(const nri_linux_cpu *src, nri_linux_cpu **dest)
+{
+ if (src == NULL || dest == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+
+ (*dest) = (nri_linux_cpu *)util_common_calloc_s(sizeof(nri_linux_cpu));
+ if ((*dest) == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ (*dest)->cpus = util_strdup_s(src->cpus);
+ (*dest)->mems = util_strdup_s(src->mems);
+ if (src->period != NULL) {
+ (*dest)->period = (uint64_t *)util_common_calloc_s(sizeof(uint64_t));
+ if ((*dest)->period == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->period = *src->period;
+ }
+
+ if (src->quota != NULL) {
+ (*dest)->quota = (int64_t *)util_common_calloc_s(sizeof(int64_t));
+ if ((*dest)->quota == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->quota = *src->quota;
+ }
+
+ if (src->realtime_period != NULL) {
+ (*dest)->realtime_period = (uint64_t *)util_common_calloc_s(sizeof(uint64_t));
+ if ((*dest)->realtime_period == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->realtime_period = *src->realtime_period;
+ }
+
+ if (src->realtime_runtime != NULL) {
+ (*dest)->realtime_runtime = (int64_t *)util_common_calloc_s(sizeof(int64_t));
+ if ((*dest)->realtime_runtime == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->realtime_runtime = *src->realtime_runtime;
+ }
+
+ if (src->shares != NULL) {
+ (*dest)->shares = (uint64_t *)util_common_calloc_s(sizeof(uint64_t));
+ if ((*dest)->shares == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->shares = *src->shares;
+ }
+
+ return true;
+}
+
+static bool copy_nri_linux_memory(const nri_linux_memory *src, nri_linux_memory **dest)
+{
+ if (src == NULL || dest == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+ *dest = (nri_linux_memory *)util_common_calloc_s(sizeof(nri_linux_memory));
+ if (dest == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ if (src->limit != NULL) {
+ (*dest)->limit = (int64_t *)util_common_calloc_s(sizeof(int64_t));
+ if ((*dest)->limit == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->limit = *src->limit;
+ }
+
+ if (src->reservation != NULL) {
+ (*dest)->reservation = (int64_t *)util_common_calloc_s(sizeof(int64_t));
+ if ((*dest)->reservation == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->reservation = *src->reservation;
+ }
+
+ if (src->swap != NULL) {
+ (*dest)->swap = (int64_t *)util_common_calloc_s(sizeof(int64_t));
+ if ((*dest)->swap == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->swap = *src->swap;
+ }
+
+ if (src->kernel != NULL) {
+ (*dest)->kernel = (int64_t *)util_common_calloc_s(sizeof(int64_t));
+ if ((*dest)->kernel == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->kernel = *src->kernel;
+ }
+
+
+ if (src->kernel_tcp != NULL) {
+ (*dest)->kernel_tcp = (int64_t *)util_common_calloc_s(sizeof(int64_t));
+ if ((*dest)->kernel_tcp == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->kernel_tcp = *src->kernel_tcp;
+ }
+
+ if (src->swappiness != NULL) {
+ (*dest)->swappiness = (uint64_t *)util_common_calloc_s(sizeof(uint64_t));
+ if ((*dest)->swappiness == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->swappiness = *src->swappiness;
+ }
+
+ if (src->disable_oom_killer != NULL) {
+ (*dest)->disable_oom_killer = (uint8_t *)util_common_calloc_s(sizeof(uint8_t));
+ if ((*dest)->disable_oom_killer == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->disable_oom_killer = *src->disable_oom_killer;
+ }
+
+ if (src->use_hierarchy != NULL) {
+ (*dest)->use_hierarchy = (uint8_t *)util_common_calloc_s(sizeof(uint8_t));
+ if ((*dest)->use_hierarchy == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ *(*dest)->use_hierarchy = *src->use_hierarchy;
+ }
+ return true;
+}
+
+bool is_marked_for_removal(const char* key, char **out)
+{
+ if (key == NULL || out == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+
+ if (!util_has_prefix(key, "-")) {
+ *out = (char*)key;
+ return false;
+ }
+
+ *out = util_sub_string(key, 1, strlen(key) - 1);
+ if (*out == NULL) {
+ ERROR("Failed to sub string");
+ return false;
+ }
+
+ return true;
+}
+
+bool copy_nri_mount(const nri_mount *src, nri_mount **dest)
+{
+ if (src == NULL || dest == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+ *dest = (nri_mount *)util_common_calloc_s(sizeof(nri_mount));
+ if (dest == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ (*dest)->destination = util_strdup_s(src->destination);
+ (*dest)->options = util_copy_array_by_len(src->options, src->options_len);
+ (*dest)->options_len = src->options_len;
+ (*dest)->source = util_strdup_s(src->source);
+ (*dest)->type = util_strdup_s(src->type);
+ return true;
+}
+
+bool copy_nri_key_value(const nri_key_value *src, nri_key_value **dest)
+{
+ if (src == NULL || dest == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+ *dest = (nri_key_value *)util_common_calloc_s(sizeof(nri_key_value));
+ if (dest == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ (*dest)->key = util_strdup_s(src->key);
+ (*dest)->value = util_strdup_s(src->value);
+ return true;
+}
+
+bool copy_nri_posix_rlimit(const nri_posix_rlimit *src, nri_posix_rlimit **dest)
+{
+ if (src == NULL || dest == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+ *dest = (nri_posix_rlimit *)util_common_calloc_s(sizeof(nri_posix_rlimit));
+ if (dest == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+ (*dest)->hard = src->hard;
+ (*dest)->soft = src->soft;
+ (*dest)->type = util_strdup_s(src->type);
+ return true;
+}
+
+bool copy_nri_linux_resources(const nri_linux_resources *src, nri_linux_resources **dest)
+{
+ if (src == NULL || dest == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+
+ *dest = (nri_linux_resources *)util_common_calloc_s(sizeof(nri_linux_resources));
+ if (*dest == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+
+ if (!init_nri_linux_resources(dest)) {
+ ERROR("Failed to init dest nri linux resources");
+ goto free_out;
+ }
+
+ if (!copy_nri_linux_cpu(src->cpu, &(*dest)->cpu)) {
+ ERROR("Failed to copy nri_linux_cpu");
+ goto free_out;
+ }
+
+ if (!copy_nri_linux_memory(src->memory, &(*dest)->memory)) {
+ ERROR("Failed to copy nri_linux_memory");
+ goto free_out;
+ }
+
+ (*dest)->blockio_class = util_strdup_s(src->blockio_class);
+ (*dest)->rdt_class = util_strdup_s(src->rdt_class);
+
+ if (src->hugepage_limits_len > 0) {
+ (*dest)->hugepage_limits = (nri_hugepage_limit**)util_smart_calloc_s(sizeof(nri_hugepage_limit*),
+ src->hugepage_limits_len);
+ for (size_t i = 0; i < src->hugepage_limits_len; ++i) {
+ if (!copy_nri_hugepage_limit(src->hugepage_limits[i], &((*dest)->hugepage_limits[i]))) {
+ ERROR("Failed to copy nri_hugepage_limit");
+ goto free_out;
+ }
+ }
+ }
+
+ if (src->devices_len > 0) {
+ (*dest)->devices = (nri_linux_device_cgroup**)util_smart_calloc_s(sizeof(nri_linux_device_cgroup*), src->devices_len);
+ for (size_t i = 0; i < src->devices_len; ++i) {
+ if (!copy_nri_linux_device_cgroup(src->devices[i], &((*dest)->devices[i]))) {
+ ERROR("Failed to copy nri_linux_device_cgroup");
+ goto free_out;
+ }
+ }
+ }
+
+ if (dup_json_map_string_string(src->unified, (*dest)->unified)) {
+ ERROR("Failed to copy json_map_string_string");
+ goto free_out;
+ }
+
+ return true;
+
+free_out:
+ free_nri_linux_resources(*dest);
+ return false;
+}
+
+bool merge_nri_hooks(nri_hook **targetHooks, size_t targetSize, const nri_hook **sourceHooks,
+ size_t sourceLen)
+{
+ size_t oldSize = targetSize * sizeof(nri_hook *);
+ size_t newSize = oldSize + sourceLen * sizeof(nri_hook *);
+
+ if (sourceHooks == NULL || targetHooks == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+
+ if (util_mem_realloc((void**)&targetHooks, newSize, (void**)&targetHooks, oldSize) != 0) {
+ ERROR("Failed to realloc and assign hook array");
+ return false;
+ }
+
+ for (size_t i = 0; i < sourceLen; i++) {
+ if (!copy_nri_hook(sourceHooks[i], &targetHooks[targetSize++])) {
+ ERROR("Failed to copy hook");
+ return false;
+ }
+ }
+
+ return true;
+}
+
+bool init_nri_container_adjust(nri_container_adjustment **adjust)
+{
+ if (adjust == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+
+ *adjust = (nri_container_adjustment *)util_common_calloc_s(sizeof(nri_container_adjustment));
+ if (*adjust == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+
+ (*adjust)->annotations = (json_map_string_string *)util_common_calloc_s(sizeof(json_map_string_string));
+ if ((*adjust)->annotations == NULL) {
+ goto free_out;
+ }
+
+ (*adjust)->env = (nri_key_value **)util_common_calloc_s(sizeof(nri_key_value *));
+ if ((*adjust)->env == NULL) {
+ goto free_out;
+ }
+ (*adjust)->env_len = 0;
+
+ (*adjust)->hooks = (nri_hooks *)util_common_calloc_s(sizeof(nri_hooks));
+ if ((*adjust)->hooks == NULL) {
+ goto free_out;
+ }
+
+ (*adjust)->linux = (nri_linux_container_adjustment *)util_common_calloc_s(sizeof(nri_linux_container_adjustment));
+ if ((*adjust)->linux == NULL) {
+ goto free_out;
+ }
+
+ (*adjust)->linux->resources = (nri_linux_resources *)util_common_calloc_s(sizeof(nri_linux_resources));
+ if ((*adjust)->linux->resources == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+
+ (*adjust)->mounts = (nri_mount **)util_common_calloc_s(sizeof(nri_mount *));
+ if ((*adjust)->mounts == NULL) {
+ goto free_out;
+ }
+ (*adjust)->mounts_len = 0;
+
+ (*adjust)->rlimits = (nri_posix_rlimit **)util_common_calloc_s(sizeof(nri_posix_rlimit *));
+ if ((*adjust)->rlimits == NULL) {
+ goto free_out;
+ }
+ (*adjust)->rlimits_len = 0;
+
+ return true;
+
+free_out:
+ ERROR("Out of memory");
+ free_nri_container_adjustment(*adjust);
+ return false;
+}
+
+bool init_nri_container_update(nri_container_update **update, const char *id, uint8_t ignore_failure)
+{
+ if (update == NULL || id == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+
+ *update = (nri_container_update *)util_common_calloc_s(sizeof(nri_container_update));
+ if (*update == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+
+ (*update)->container_id = util_strdup_s(id);
+ (*update)->linux = (nri_linux_container_update *)util_common_calloc_s(sizeof(nri_linux_container_update));
+ if ((*update)->linux == NULL) {
+ goto free_out;
+ }
+
+ (*update)->ignore_failure = ignore_failure;
+ return true;
+
+free_out:
+ ERROR("Out of memory");
+ free_nri_container_update(*update);
+ return false;
+}
+
+bool init_nri_linux_resources(nri_linux_resources **resources)
+{
+ if (resources == NULL) {
+ ERROR("Invalid input arguments");
+ return false;
+ }
+
+ *resources = (nri_linux_resources *)util_common_calloc_s(sizeof(nri_linux_resources));
+ if (*resources == NULL) {
+ ERROR("Out of memory");
+ return false;
+ }
+
+ (*resources)->cpu = (nri_linux_cpu *)util_common_calloc_s(sizeof(nri_linux_cpu));
+ if ((*resources)->cpu == NULL) {
+ goto free_out;
+ }
+
+ (*resources)->memory = (nri_linux_memory *)util_common_calloc_s(sizeof(nri_linux_memory));
+ if ((*resources)->memory == NULL) {
+ goto free_out;
+ }
+
+ (*resources)->unified = (json_map_string_string *)util_common_calloc_s(sizeof(json_map_string_string));
+ if ((*resources)->unified == NULL) {
+ goto free_out;
+ }
+ return true;
+
+free_out:
+ ERROR("Out of memory");
+ free_nri_linux_resources(*resources);
+ return false;
+}
\ No newline at end of file
diff --git a/src/daemon/common/nri/nri_utils.h b/src/daemon/common/nri/nri_utils.h
index 3aa50ae4..7bf54a71 100644
--- a/src/daemon/common/nri/nri_utils.h
+++ b/src/daemon/common/nri/nri_utils.h
@@ -51,14 +51,13 @@ typedef enum {
bool copy_nri_mount(const nri_mount *src, nri_mount **dest);
bool copy_nri_key_value(const nri_key_value *src, nri_key_value **dest);
-bool copy_nri_hook(const nri_hook *src, nri_hook **dest);
bool copy_nri_posix_rlimit(const nri_posix_rlimit *src, nri_posix_rlimit **dest);
bool copy_nri_linux_resources(const nri_linux_resources *src, nri_linux_resources **dest);
-bool copy_nri_linux_cpu(const nri_linux_cpu *src, nri_linux_cpu **dest);
bool is_marked_for_removal(const char* key, char **out);
-bool realloc_and_copy_nri_hooks(nri_hook **targetHooks, size_t targetSize, const nri_hook **sourceHooks, size_t sourceLen);
+bool merge_nri_hooks(nri_hook **targetHooks, size_t targetSize, const nri_hook **sourceHooks,
+ size_t sourceLen);
bool init_nri_container_adjust(nri_container_adjustment **adjust);
bool init_nri_container_update(nri_container_update **update, const char *id, uint8_t ignore_failure);
diff --git a/src/daemon/config/isulad_config.c b/src/daemon/config/isulad_config.c
index d7b54498..9ba1c8a0 100644
--- a/src/daemon/config/isulad_config.c
+++ b/src/daemon/config/isulad_config.c
@@ -456,6 +456,175 @@ out:
(void)isulad_server_conf_unlock();
return path;
}
+
+#ifdef ENABLE_NRI
+bool conf_get_nri_support(void)
+{
+ bool nri_support = false;
+ struct service_arguments *conf = NULL;
+
+ if (isulad_server_conf_rdlock() != 0) {
+ return false;
+ }
+
+ conf = conf_get_server_conf();
+ if (conf == NULL || conf->json_confs == NULL) {
+ goto out;
+ }
+
+ nri_support = conf->json_confs->nri_support;
+
+out:
+ (void)isulad_server_conf_unlock();
+ return nri_support;
+}
+
+bool conf_get_nri_external_support(void)
+{
+ bool nri_external_support = false;
+ struct service_arguments *conf = NULL;
+
+ if (isulad_server_conf_rdlock() != 0) {
+ return false;
+ }
+
+ conf = conf_get_server_conf();
+ if (conf == NULL || conf->json_confs == NULL) {
+ goto out;
+ }
+
+ nri_external_support = conf->json_confs->disable_connections;
+
+out:
+ (void)isulad_server_conf_unlock();
+ return !nri_external_support;
+}
+
+char *conf_get_nri_plugin_config_path(void)
+{
+ char *path = NULL;
+ struct service_arguments *conf = NULL;
+
+ if (isulad_server_conf_rdlock() != 0) {
+ return NULL;
+ }
+
+ conf = conf_get_server_conf();
+ if (conf == NULL || conf->json_confs == NULL || conf->json_confs->plugin_config_path == NULL) {
+ path = util_strdup_s(DEFAULT_PLUGIN_CONFIG_PATH);
+ goto out;
+ }
+
+ path = util_strdup_s(conf->json_confs->plugin_config_path);
+
+out:
+ (void)isulad_server_conf_unlock();
+ return path;
+}
+
+char *conf_get_nri_plugin_path(void)
+{
+ char *path = NULL;
+ struct service_arguments *conf = NULL;
+
+ if (isulad_server_conf_rdlock() != 0) {
+ return NULL;
+ }
+
+ conf = conf_get_server_conf();
+ if (conf == NULL || conf->json_confs == NULL) {
+ goto out;
+ }
+
+ if (conf->json_confs->plugin_path == NULL) {
+ path = util_strdup_s(DEFAULT_PLUGIN_PATH);
+ goto out;
+ }
+
+ path = util_strdup_s(conf->json_confs->plugin_path);
+
+out:
+ (void)isulad_server_conf_unlock();
+ return path;
+}
+
+char *conf_get_socket_path(void)
+{
+ char *path = NULL;
+ struct service_arguments *conf = NULL;
+
+ if (isulad_server_conf_rdlock() != 0) {
+ return NULL;
+ }
+
+ conf = conf_get_server_conf();
+ if (conf == NULL || conf->json_confs == NULL) {
+ goto out;
+ }
+
+ if (conf->json_confs->nri_socket_path == NULL) {
+ path = util_strdup_s(DEFAULT_SOCKET_PATH);
+ goto out;
+ }
+
+ path = util_strdup_s(conf->json_confs->nri_socket_path);
+
+out:
+ (void)isulad_server_conf_unlock();
+ return path;
+}
+
+uint64_t conf_get_nri_plugin_registration_timeout(void)
+{
+ uint64_t timeout = false;
+ struct service_arguments *conf = NULL;
+
+ if (isulad_server_conf_rdlock() != 0) {
+ return false;
+ }
+
+ conf = conf_get_server_conf();
+ if (conf == NULL || conf->json_confs == NULL) {
+ goto out;
+ }
+
+ if (conf->json_confs->plugin_registration_timeout == 0) {
+ timeout = DEFAULT_PLUGIN_REGISTRY_TIMEOUT;
+ goto out;
+ }
+
+ timeout = conf->json_confs->plugin_registration_timeout;
+
+out:
+ (void)isulad_server_conf_unlock();
+ return timeout;
+}
+uint64_t conf_get_nri_plugin_requst_timeout(void)
+{
+ uint64_t timeout = false;
+ struct service_arguments *conf = NULL;
+
+ if (isulad_server_conf_rdlock() != 0) {
+ return false;
+ }
+
+ conf = conf_get_server_conf();
+ if (conf == NULL || conf->json_confs == NULL) {
+ goto out;
+ }
+
+ if (conf->json_confs->plugin_requst_timeout == 0) {
+ timeout = DEFAULT_PLUGIN_REQUST_TIMEOUT;
+ goto out;
+ }
+
+ timeout = conf->json_confs->plugin_requst_timeout;
+
+out:
+ (void)isulad_server_conf_unlock();
+ return timeout;
+}
+#endif
#endif
/* conf get isulad rootdir */
@@ -1762,6 +1931,15 @@ int merge_json_confs_into_global(struct service_arguments *args)
tmp_json_confs->cri_sandboxers = NULL;
#endif
args->json_confs->enable_cri_v1 = tmp_json_confs->enable_cri_v1;
+#ifdef ENABLE_NRI
+ args->json_confs->nri_support = tmp_json_confs->nri_support;
+ args->json_confs->disable_connections = tmp_json_confs->disable_connections;
+ override_string_value(&args->json_confs->plugin_config_path, &tmp_json_confs->plugin_config_path);
+ override_string_value(&args->json_confs->plugin_path, &tmp_json_confs->plugin_path);
+ args->json_confs->plugin_registration_timeout = tmp_json_confs->plugin_registration_timeout;
+ args->json_confs->plugin_requst_timeout = tmp_json_confs->plugin_requst_timeout;
+ override_string_value(&args->json_confs->nri_socket_path, &tmp_json_confs->nri_socket_path);
+#endif
args->json_confs->enable_pod_events = tmp_json_confs->enable_pod_events;
#endif
diff --git a/src/daemon/modules/api/specs_api.h b/src/daemon/modules/api/specs_api.h
index 6a1cd776..d5ea0c7c 100644
--- a/src/daemon/modules/api/specs_api.h
+++ b/src/daemon/modules/api/specs_api.h
@@ -76,6 +76,11 @@ int spec_add_linux_resources_hugepage_limit(oci_runtime_spec *oci_spec, const ch
int spec_add_linux_resources_rlimit(oci_runtime_spec *oci_spec, const char *type, uint64_t hard, uint64_t soft);
#endif /* ENABLE_NRI */
+int make_sure_oci_spec_annotations(oci_runtime_spec *oci_spec);
+int make_sure_oci_spec_linux_resources_cpu(oci_runtime_spec *oci_spec);
+int make_sure_oci_spec_linux_resources_mem(oci_runtime_spec *oci_spec);
+int make_sure_oci_spec_hooks(oci_runtime_spec *oci_spec);
+
#ifdef __cplusplus
}
#endif
diff --git a/src/daemon/modules/spec/specs.c b/src/daemon/modules/spec/specs.c
index 1fd9e5a8..002431d8 100644
--- a/src/daemon/modules/spec/specs.c
+++ b/src/daemon/modules/spec/specs.c
@@ -87,8 +87,11 @@ struct readonly_default_oci_spec {
static struct readonly_default_oci_spec g_rdspec;
-static int make_sure_oci_spec_annotations(oci_runtime_spec *oci_spec)
+int make_sure_oci_spec_annotations(oci_runtime_spec *oci_spec)
{
+ if (oci_spec == NULL) {
+ return -1;
+ }
if (oci_spec->annotations == NULL) {
oci_spec->annotations = util_common_calloc_s(sizeof(json_map_string_string));
if (oci_spec->annotations == NULL) {
@@ -464,10 +467,14 @@ out:
return ret;
}
-static int make_sure_oci_spec_linux_resources_cpu(oci_runtime_spec *oci_spec)
+int make_sure_oci_spec_linux_resources_cpu(oci_runtime_spec *oci_spec)
{
int ret = 0;
+ if (oci_spec == NULL) {
+ return -1;
+ }
+
ret = make_sure_oci_spec_linux_resources(oci_spec);
if (ret < 0) {
return -1;
@@ -589,10 +596,14 @@ out:
return ret;
}
-static int make_sure_oci_spec_linux_resources_mem(oci_runtime_spec *oci_spec)
+int make_sure_oci_spec_linux_resources_mem(oci_runtime_spec *oci_spec)
{
int ret = 0;
+ if (oci_spec == NULL) {
+ return -1;
+ }
+
ret = make_sure_oci_spec_linux_resources(oci_spec);
if (ret < 0) {
return -1;
@@ -731,8 +742,11 @@ out:
return ret;
}
-static int make_sure_oci_spec_hooks(oci_runtime_spec *oci_spec)
+int make_sure_oci_spec_hooks(oci_runtime_spec *oci_spec)
{
+ if (oci_spec == NULL) {
+ return -1;
+ }
if (oci_spec->hooks == NULL) {
oci_spec->hooks = util_common_calloc_s(sizeof(oci_runtime_spec_hooks));
if (oci_spec->hooks == NULL) {
@@ -2827,6 +2841,11 @@ int spec_add_linux_resources_hugepage_limit(oci_runtime_spec *oci_spec, const ch
int ret = 0;
defs_resources_hugepage_limits_element *hugepage_limit = NULL;
+ if (oci_spec == NULL || page_size == NULL) {
+ ERROR("Invalid arguments");
+ return -1;
+ }
+
ret = make_sure_oci_spec_linux_resources(oci_spec);
if (ret < 0) {
return -1;
@@ -2859,6 +2878,11 @@ int spec_add_linux_resources_rlimit(oci_runtime_spec *oci_spec, const char *type
int ret = 0;
defs_process_rlimits_element *rlimit = NULL;
+ if (oci_spec == NULL || type == NULL) {
+ ERROR("Invalid arguments");
+ return -1;
+ }
+
ret = make_sure_oci_spec_linux_resources(oci_spec);
if (ret < 0) {
return -1;
diff --git a/src/daemon/nri/nri_adaption.h b/src/daemon/nri/nri_adaption.h
index 7f0640df..874662cf 100644
--- a/src/daemon/nri/nri_adaption.h
+++ b/src/daemon/nri/nri_adaption.h
@@ -46,7 +46,6 @@ public:
auto GetSockpath(std::vector<std::string> &paths) -> bool;
- // Stop plugins.
auto StopPlugins() -> bool;
void RemoveClosedPlugins();
@@ -58,19 +57,23 @@ public:
auto RunPodSandbox(std::shared_ptr<const sandbox::Sandbox> sandbox, Errors &error) ->bool;
auto StopPodSandbox(std::shared_ptr<const sandbox::Sandbox> sandbox, Errors &error) ->bool;
auto RemovePodSandbox(std::shared_ptr<const sandbox::Sandbox> sandbox, Errors &error) ->bool;
- auto CreateContainer(std::shared_ptr<const sandbox::Sandbox> sandbox, const std::string &conId, const runtime::v1::ContainerConfig &containerConfig, nri_container_adjustment **adjust, Errors &error) -> bool;
- auto PostCreateContainer(const std::string &conId, Errors &error) ->bool;
- auto UndoCreateContainer(std::shared_ptr<const sandbox::Sandbox> sandbox, const std::string &conId, Errors &error) -> bool;
- auto StartContainer(const std::string &conId, Errors &error) ->bool;
- auto PostStartContainer(const std::string &conId, Errors &error) ->bool;
- auto UpdateContainer(const std::string &conId, Errors &error) ->bool;
- auto PostUpdateContainer(const std::string &conId, Errors &error) ->bool;
- auto StopContainer(const std::string &conId, Errors &error) ->bool;
- auto RemoveContainer(const std::string &conId, Errors &error) ->bool;
- auto StateChange(nri_state_change_event *evt, Errors &error) ->bool;
- auto updateContainers(const nri_update_containers_request *req, nri_update_containers_response **resp) ->bool;
+ auto CreateContainer(std::shared_ptr<const sandbox::Sandbox> sandbox, const std::string &conId,
+ const runtime::v1::ContainerConfig &containerConfig, nri_container_adjustment **adjust,
+ Errors &error) -> bool;
+ auto PostCreateContainer(const std::string &conId, Errors &error) -> bool;
+ auto UndoCreateContainer(std::shared_ptr<const sandbox::Sandbox> sandbox, const std::string &conId,
+ Errors &error) -> bool;
+ auto StartContainer(const std::string &conId, Errors &error) -> bool;
+ auto PostStartContainer(const std::string &conId, Errors &error) -> bool;
+ auto UpdateContainer(const std::string &conId, Errors &error) -> bool;
+ auto PostUpdateContainer(const std::string &conId, Errors &error) -> bool;
+ auto StopContainer(const std::string &conId, Errors &error) -> bool;
+ auto RemoveContainer(const std::string &conId, Errors &error) -> bool;
+ auto StateChange(nri_state_change_event *evt, Errors &error) -> bool;
+ auto updateContainers(const nri_update_containers_request *req, nri_update_containers_response **resp) -> bool;
auto NewExternalPlugin(int fd) -> bool;
+
private:
NRIAdaptation() = default;
NRIAdaptation(const NRIAdaptation &other) = delete;
@@ -86,18 +89,25 @@ private:
auto SortPlugins() -> bool;
void GetClosedPlugins(std::vector<std::string> &closedPlugin);
- auto IsSupport() -> bool;
+ auto ApplyUpdates(const std::vector<nri_container_update *> &update, std::vector<nri_container_update *> &failed,
+ bool getFailed, Errors &error) -> bool;
- auto ApplyUpdates(const std::vector<nri_container_update *> &update, std::vector<nri_container_update *> &failed, bool getFailed,
- Errors &error) -> bool;
+ auto IsSupport() -> bool;
- auto NRIPodSandbox(const std::shared_ptr<const sandbox::Sandbox> &sandbox, Errors& error) -> std::unique_ptr<CStructWrapper<nri_pod_sandbox>>;
- auto NRIContainerByConConfig(const std::shared_ptr<const sandbox::Sandbox> &sandbox, const runtime::v1::ContainerConfig &containerConfig, Errors& error) -> std::unique_ptr<CStructWrapper<nri_container>>;
- auto NRIContainerByID(const std::string &id, Errors& error) -> std::unique_ptr<CStructWrapper<nri_container>>;
+ auto NRIPodSandbox(const std::shared_ptr<const sandbox::Sandbox> &sandbox,
+ Errors &error) -> std::unique_ptr<CStructWrapper<nri_pod_sandbox>>;
+ auto NRIContainerByConConfig(const std::shared_ptr<const sandbox::Sandbox> &sandbox,
+ const runtime::v1::ContainerConfig &containerConfig, Errors &error) -> std::unique_ptr<CStructWrapper<nri_container>>;
+ auto NRIContainerByID(const std::string &id, Errors &error) -> std::unique_ptr<CStructWrapper<nri_container>>;
auto GetNRIPluginConfigPath(void) -> std::string;
auto GetNRIPluginPath(void) -> std::string;
auto GetNRISockPath(void) -> std::string;
+
+ void PluginsStateChange(nri_state_change_event *evt);
+ bool PluginsCreateContainer(nri_create_container_request *req, const std::string &conId, pluginResult &result);
+ bool PluginsUpdateContainer(nri_update_container_request *req, const std::string &conId, pluginResult &result);
+
private:
RWMutex m_mutex;
static std::atomic<NRIAdaptation *> m_instance;
diff --git a/src/daemon/nri/nri_helpers.cc b/src/daemon/nri/nri_helpers.cc
new file mode 100644
index 00000000..ff9d67c1
--- /dev/null
+++ b/src/daemon/nri/nri_helpers.cc
@@ -0,0 +1,93 @@
+/******************************************************************************
+ * Copyright (c) Huawei Technologies Co., Ltd. 2024. All rights reserved.
+ * iSulad licensed under the Mulan PSL v2.
+ * You can use this software according to the terms and conditions of the Mulan PSL v2.
+ * You may obtain a copy of Mulan PSL v2 at:
+ * http://license.coscl.org.cn/MulanPSL2
+ * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR
+ * PURPOSE.
+ * See the Mulan PSL v2 for more details.
+ * Author: zhongtao
+ * Create: 2024-07-13
+ * Description: provide nri helpers functions
+ *********************************************************************************/
+
+#include "nri_helpers.h"
+
+#include <isula_libutils/log.h>
+
+#include "utils.h"
+#include "isulad_config.h"
+
+namespace NRIHelpers {
+std::string MarkForRemoval(const std::string &key)
+{
+ return "-" + key;
+}
+
+auto GetPluginConfig(std::string &idx, std::string &name, std::string &config) -> bool
+{
+ __isula_auto_free char *plugin_path = NULL;
+
+ plugin_path = conf_get_nri_plugin_config_path();
+ if (plugin_path == NULL) {
+ return false;
+ }
+ std::string compleName = idx + "-" + name;
+ std::vector<std::string> dropIns = {
+ std::string(plugin_path) + "/" + compleName + ".conf",
+ std::string(plugin_path) + "/" + name + ".conf"
+ };
+
+ for (const std::string &path : dropIns) {
+ char buf[MAX_BUFFER_SIZE + 1] = { 0 };
+ __isula_auto_close int fd = util_open(path.c_str(), O_RDONLY, 0);
+ if (fd < 0) {
+ ERROR("Failed to open '%s'", path.c_str());
+ return false;
+ }
+ int len = util_read_nointr(fd, buf, sizeof(buf) - 1);
+ if (len < 0) {
+ SYSERROR("Failed to read nri plugin config : %s", path.c_str());
+ return false;
+ }
+ config = std::string(buf);
+ return true;
+ }
+ return true;
+}
+
+void GenerateRandomExternalName(std::string &ret)
+{
+ __isula_auto_free char *external_name = NULL;
+
+ external_name = (char *)util_smart_calloc_s(sizeof(char), (CONTAINER_ID_MAX_LEN + 1));
+ if (external_name == NULL) {
+ ERROR("Out of memory");
+ return;
+ }
+
+ if (util_generate_random_str(external_name, (size_t)CONTAINER_ID_MAX_LEN)) {
+ ERROR("Generate exec suffix failed");
+ return;
+ }
+
+ ret = std::string(external_name);
+}
+
+bool CheckPluginIndex(const std::string &idx)
+{
+ if (idx.length() != 2) {
+ ERROR("Invalid plugin index \"%s\", must be 2 digits", idx.c_str());
+ return false;
+ }
+
+ if (!std::isdigit(idx[0]) || !std::isdigit(idx[1])) {
+ ERROR("Invalid plugin index \"%s\", (not [0-9][0-9])", idx.c_str());
+ return false;
+ }
+
+ return true;
+}
+}// namespace NRIHelpers
\ No newline at end of file
diff --git a/src/daemon/nri/nri_helpers.h b/src/daemon/nri/nri_helpers.h
index 06ee8419..1a2f488e 100644
--- a/src/daemon/nri/nri_helpers.h
+++ b/src/daemon/nri/nri_helpers.h
@@ -37,7 +37,7 @@ std::string MarkForRemoval(const std::string &key);
auto GetPluginConfig(std::string &idx, std::string &name, std::string &config) -> bool;
-std::string GenerateRandomExternalName(void);
+void GenerateRandomExternalName(std::string &ret);
bool CheckPluginIndex(const std::string &idx);
diff --git a/src/utils/cpputils/transform.cc b/src/utils/cpputils/transform.cc
index 51c154fb..ba8c1f7a 100644
--- a/src/utils/cpputils/transform.cc
+++ b/src/utils/cpputils/transform.cc
@@ -97,7 +97,7 @@ auto RepeatedPtrFieldToCharArray(const google::protobuf::RepeatedPtrField<std::s
if (result == nullptr) {
return nullptr;
}
- size_t i {};
+ size_t i = 0;
for (const auto &it : ptrs) {
result[i++] = util_strdup_s(it.c_str());
}
--
2.25.1