From 06e6904d397ef0ec41ab532881a9e274db829c1b Mon Sep 17 00:00:00 2001 From: Igor Bezukh Date: Wed, 12 Feb 2025 20:14:50 +0200 Subject: [PATCH] discontinue support of OCI hook maintaining of the OCI hook becomes expensive - the hook is tightly coupled with the specific OCI runtime that was chosen to be used on the node. Moreover the hook cannot be adjusted on a per-pod basis when the pod is using a custom runtime class. In addition the OCI hook is detached from the wasp-agent lifecycle. It means that extra effort needs to be put in order to clean the hook when the wasp-agent is unresponsive or when its deleted from the cluster. if we consider to remove the hook we should compare two scenarios - with and w/o the hook. The difference is as follows: (1) with the hook the transition is unlimited->limited swap usage. (2) w/o the hook the transition is zero->limited swap usage. setting the limited swap is done by the limited swap controller which runs inside the wasp-agent daemonset. The time it takes to set the limited swap depends on the API latency (this design by itself can be improved). by switching from (1) to (2) we actually don't introduce regression from workload stability perspective, because in both scenarios if the workload exceeds its allowed limited swap, it will be OOMkilled. From node stability perspective switching to (2) is even safer. scenario (2) puts in risk only the container itself that could be OOMkilled in the worst case, while in scenario (1) unlimited swap consumption can put the whole node in risk. Regarding API latency the following steps can be taken: (*) We actually don't need the API server, we can work directly with the kubelet server. (**) We can utilize NRI, thus opt-in for limited swap from inside the CRI lifecycle. Signed-off-by: Igor Bezukh --- Containerfile.wasp | 1 - OCI-hook/hook.sh | 14 -------------- OCI-hook/swap-for-burstable.json | 12 ------------ pkg/wasp/application.go | 13 ------------- 4 files changed, 40 deletions(-) delete mode 100644 OCI-hook/hook.sh delete mode 100644 OCI-hook/swap-for-burstable.json diff --git a/Containerfile.wasp b/Containerfile.wasp index 555633c6..2efb3f41 100644 --- a/Containerfile.wasp +++ b/Containerfile.wasp @@ -26,7 +26,6 @@ FROM fedora:38 # Copy the binary from the builder stage to the final image COPY --from=builder /workdir/app/wasp /app/wasp -COPY OCI-hook /app/OCI-hook # Set the working directory to /app WORKDIR /app diff --git a/OCI-hook/hook.sh b/OCI-hook/hook.sh deleted file mode 100644 index 9fb23622..00000000 --- a/OCI-hook/hook.sh +++ /dev/null @@ -1,14 +0,0 @@ -#!/usr/bin/bash - -echo "WASP SWAP hook" - -set -x - -CG_PATH=$(jq -er '.linux.cgroupsPath' < config.json) -POD_NAMESPACE=$(jq -er '.annotations["io.kubernetes.pod.namespace"]' < config.json) - -if [[ "$CG_PATH" =~ .*"burst".* ]]; -then - CONTAINERID=$(jq -er '.linux.cgroupsPath | split(":")[2]' < config.json) - runc update $CONTAINERID --memory-swap -1 -fi diff --git a/OCI-hook/swap-for-burstable.json b/OCI-hook/swap-for-burstable.json deleted file mode 100644 index 1846ff2a..00000000 --- a/OCI-hook/swap-for-burstable.json +++ /dev/null @@ -1,12 +0,0 @@ -{ - "version": "1.0.0", - "hook": { - "path": "/opt/oci-hook-swap.sh" - }, - "when": { - "always": true - }, - "stages": [ - "poststart" - ] -} \ No newline at end of file diff --git a/pkg/wasp/application.go b/pkg/wasp/application.go index e80b1a1a..637c2940 100644 --- a/pkg/wasp/application.go +++ b/pkg/wasp/application.go @@ -59,7 +59,6 @@ func Execute() { flag.Parse() setCrioSocketSymLink() - setOCIHook() var app = WaspApp{} swapUtilizationThresholdFactorStr := os.Getenv("SWAP_UTILIZATION_THRESHOLD_FACTOR") @@ -201,18 +200,6 @@ func setCrioSocketSymLink() { } } -func setOCIHook() { - err := moveFile("/app/OCI-hook/hook.sh", "/host/opt/oci-hook-swap.sh") - if err != nil { - klog.Warningf(err.Error()) - return - } - err = moveFile("/app/OCI-hook/swap-for-burstable.json", "/host/run/containers/oci/hooks.d/swap-for-burstable.json") - if err != nil { - klog.Warningf(err.Error()) - } -} - func moveFile(sourcePath, destPath string) error { inputFile, err := os.Open(sourcePath) if err != nil {