From 2904b5e8cb87f89939e80b896980a6ed32462658 Mon Sep 17 00:00:00 2001 From: Brandon Palm Date: Wed, 10 Jun 2026 12:55:43 -0500 Subject: [PATCH] CM-1113: Replace unsafe.Pointer casts with Kubernetes conversion functions Replace raw unsafe.Pointer casts between corev1 and core types with the auto-generated conversion functions from k8s.io/kubernetes/pkg/apis/core/v1. This removes all unsafe imports from validation and deployment helper code while delegating type conversion to upstream-maintained functions. --- .../certmanager/deployment_helper.go | 17 +++------ .../deployment_overrides_validation.go | 8 +--- pkg/controller/common/validation.go | 37 ++++++++++++++----- 3 files changed, 35 insertions(+), 27 deletions(-) diff --git a/pkg/controller/certmanager/deployment_helper.go b/pkg/controller/certmanager/deployment_helper.go index f26c92ecb..38615fb69 100644 --- a/pkg/controller/certmanager/deployment_helper.go +++ b/pkg/controller/certmanager/deployment_helper.go @@ -4,14 +4,13 @@ import ( "fmt" "sort" "strings" - "unsafe" corev1 "k8s.io/api/core/v1" "k8s.io/apimachinery/pkg/labels" - "k8s.io/kubernetes/pkg/apis/core" "k8s.io/kubernetes/pkg/util/tolerations" "github.com/openshift/cert-manager-operator/api/operator/v1alpha1" + "github.com/openshift/cert-manager-operator/pkg/controller/common" certmanagerinformer "github.com/openshift/cert-manager-operator/pkg/operator/informers/externalversions/operator/v1alpha1" ) @@ -116,15 +115,11 @@ func mergePodScheduling(sourceScheduling v1alpha1.CertManagerScheduling, overrid // Merge the source and override NodeSelector. mergedNodeSelector := labels.Merge(sourceScheduling.NodeSelector, overrideScheduling.NodeSelector) - // Convert corev1.Tolerations to core.Tolerations. - sourceTolerations := *(*[]core.Toleration)(unsafe.Pointer(&sourceScheduling.Tolerations)) - overridingTolerations := *(*[]core.Toleration)(unsafe.Pointer(&overrideScheduling.Tolerations)) - - // Merge the source and override Tolerations. - mergedCoreTolerations := tolerations.MergeTolerations(sourceTolerations, overridingTolerations) - - // Convert core.Tolerations to corev1.Tolerations. - mergedCorev1Tolerations := *(*[]corev1.Toleration)(unsafe.Pointer(&mergedCoreTolerations)) + mergedCoreTolerations := tolerations.MergeTolerations( + common.ToCoreTolerations(sourceScheduling.Tolerations), + common.ToCoreTolerations(overrideScheduling.Tolerations), + ) + mergedCorev1Tolerations := common.ToV1Tolerations(mergedCoreTolerations) return v1alpha1.CertManagerScheduling{ NodeSelector: mergedNodeSelector, diff --git a/pkg/controller/certmanager/deployment_overrides_validation.go b/pkg/controller/certmanager/deployment_overrides_validation.go index 8aa9fa5a1..fccfaec62 100644 --- a/pkg/controller/certmanager/deployment_overrides_validation.go +++ b/pkg/controller/certmanager/deployment_overrides_validation.go @@ -2,20 +2,19 @@ package certmanager import ( "fmt" - "unsafe" appsv1 "k8s.io/api/apps/v1" corev1 "k8s.io/api/core/v1" metav1validation "k8s.io/apimachinery/pkg/apis/meta/v1/validation" utilerrors "k8s.io/apimachinery/pkg/util/errors" "k8s.io/apimachinery/pkg/util/validation/field" - "k8s.io/kubernetes/pkg/apis/core" corevalidation "k8s.io/kubernetes/pkg/apis/core/validation" "k8s.io/utils/strings/slices" operatorv1 "github.com/openshift/api/operator/v1" "github.com/openshift/cert-manager-operator/api/operator/v1alpha1" + "github.com/openshift/cert-manager-operator/pkg/controller/common" certmanagerinformer "github.com/openshift/cert-manager-operator/pkg/operator/informers/externalversions/operator/v1alpha1" ) @@ -300,10 +299,7 @@ func withPodSchedulingValidateHook(certmanagerinformer certmanagerinformer.CertM func validateScheduling(scheduling v1alpha1.CertManagerScheduling, fldPath *field.Path) error { errs := metav1validation.ValidateLabels(scheduling.NodeSelector, fldPath.Child("nodeSelector")) - // Convert corev1.Tolerations to core.Tolerations. - tolerations := *(*[]core.Toleration)(unsafe.Pointer(&scheduling.Tolerations)) - - errs = append(errs, corevalidation.ValidateTolerations(tolerations, fldPath.Child("tolerations"))...) + errs = append(errs, corevalidation.ValidateTolerations(common.ToCoreTolerations(scheduling.Tolerations), fldPath.Child("tolerations"))...) return errs.ToAggregate() } diff --git a/pkg/controller/common/validation.go b/pkg/controller/common/validation.go index eafb1e211..76d15be6f 100644 --- a/pkg/controller/common/validation.go +++ b/pkg/controller/common/validation.go @@ -1,13 +1,12 @@ package common import ( - "unsafe" - corev1 "k8s.io/api/core/v1" apivalidation "k8s.io/apimachinery/pkg/api/validation" metav1validation "k8s.io/apimachinery/pkg/apis/meta/v1/validation" "k8s.io/apimachinery/pkg/util/validation/field" "k8s.io/kubernetes/pkg/apis/core" + corev1conversion "k8s.io/kubernetes/pkg/apis/core/v1" corevalidation "k8s.io/kubernetes/pkg/apis/core/validation" ) @@ -20,25 +19,23 @@ func ValidateNodeSelectorConfig(nodeSelector map[string]string, fldPath *field.P // ValidateTolerationsConfig validates the Tolerations configuration using // the Kubernetes core toleration validation rules. func ValidateTolerationsConfig(tolerations []corev1.Toleration, fldPath *field.Path) error { - // convert corev1.Tolerations to core.Tolerations, required for validation. - convTolerations := *(*[]core.Toleration)(unsafe.Pointer(&tolerations)) - return corevalidation.ValidateTolerations(convTolerations, fldPath.Child("tolerations")).ToAggregate() + return corevalidation.ValidateTolerations(ToCoreTolerations(tolerations), fldPath.Child("tolerations")).ToAggregate() } // ValidateResourceRequirements validates the ResourceRequirements configuration // using the Kubernetes core resource requirements validation rules. func ValidateResourceRequirements(requirements corev1.ResourceRequirements, fldPath *field.Path) error { - // convert corev1.ResourceRequirements to core.ResourceRequirements, required for validation. - convRequirements := *(*core.ResourceRequirements)(unsafe.Pointer(&requirements)) + var convRequirements core.ResourceRequirements + _ = corev1conversion.Convert_v1_ResourceRequirements_To_core_ResourceRequirements(&requirements, &convRequirements, nil) return corevalidation.ValidateContainerResourceRequirements(&convRequirements, nil, fldPath.Child("resources"), corevalidation.PodValidationOptions{}).ToAggregate() } // ValidateAffinityRules validates the Affinity configuration using // the Kubernetes core affinity validation rules. func ValidateAffinityRules(affinity *corev1.Affinity, fldPath *field.Path) error { - // convert corev1.Affinity to core.Affinity, required for validation. - convAffinity := (*core.Affinity)(unsafe.Pointer(affinity)) - return validateAffinity(convAffinity, corevalidation.PodValidationOptions{}, fldPath.Child("affinity")).ToAggregate() + var convAffinity core.Affinity + _ = corev1conversion.Convert_v1_Affinity_To_core_Affinity(affinity, &convAffinity, nil) + return validateAffinity(&convAffinity, corevalidation.PodValidationOptions{}, fldPath.Child("affinity")).ToAggregate() } // ValidateLabelsConfig validates label keys and values using the Kubernetes @@ -52,3 +49,23 @@ func ValidateLabelsConfig(labels map[string]string, fldPath *field.Path) error { func ValidateAnnotationsConfig(annotations map[string]string, fldPath *field.Path) error { return apivalidation.ValidateAnnotations(annotations, fldPath.Child("annotations")).ToAggregate() } + +// ToCoreTolerations converts a slice of corev1.Toleration to core.Toleration +// using Kubernetes' auto-generated conversion functions. +func ToCoreTolerations(in []corev1.Toleration) []core.Toleration { + out := make([]core.Toleration, len(in)) + for i := range in { + _ = corev1conversion.Convert_v1_Toleration_To_core_Toleration(&in[i], &out[i], nil) + } + return out +} + +// ToV1Tolerations converts a slice of core.Toleration to corev1.Toleration +// using Kubernetes' auto-generated conversion functions. +func ToV1Tolerations(in []core.Toleration) []corev1.Toleration { + out := make([]corev1.Toleration, len(in)) + for i := range in { + _ = corev1conversion.Convert_core_Toleration_To_v1_Toleration(&in[i], &out[i], nil) + } + return out +}