From 9b8de48301a52b3bd9f1622f78e7e6b475b25813 Mon Sep 17 00:00:00 2001
From: Kyle Lane <kylelane@google.com>
Date: Fri, 3 Feb 2023 00:49:59 +0000
Subject: [PATCH] [Vulnerability fix] limit operator secrets permission

Also change structure to hold service account names in resource/generate/components due to circular dependancy.

Change-Id: I01c2619a9705b3c3f144d1d8567687df011d00fa
Signed-off-by: Kyle Lane kylelane@google.com
---
 manifests/generated/operator-csv.yaml.in      |  9 +++++
 .../rbac-operator.authorization.k8s.yaml.in   |  9 +++++
 pkg/virt-api/webhooks/BUILD.bazel             |  2 +-
 .../mutating-webhook/mutators/BUILD.bazel     |  2 +-
 .../mutators/vmi-mutator_test.go              |  4 +-
 pkg/virt-api/webhooks/utils.go                |  8 ++--
 .../validating-webhook/admitters/BUILD.bazel  |  2 +-
 .../admitters/vmi-create-admitter_test.go     |  9 ++---
 .../admitters/vmi-update-admitter_test.go     | 10 ++---
 .../resource/generate/components/BUILD.bazel  |  2 +-
 .../generate/components/daemonsets.go         |  3 +-
 .../generate/components/deployments.go        |  7 ++--
 .../components/serviceaccountnames.go         |  9 +++++
 .../resource/generate/rbac/BUILD.bazel        |  2 +
 .../resource/generate/rbac/apiserver.go       | 24 ++++++------
 .../resource/generate/rbac/controller.go      | 22 +++++------
 .../resource/generate/rbac/handler.go         | 22 +++++------
 .../resource/generate/rbac/operator.go        | 37 ++++++++++++-------
 .../resource/generate/rbac/operator_test.go   | 10 +++--
 19 files changed, 116 insertions(+), 77 deletions(-)
 create mode 100644 pkg/virt-operator/resource/generate/components/serviceaccountnames.go

diff --git a/manifests/generated/operator-csv.yaml.in b/manifests/generated/operator-csv.yaml.in
index 59c7b7bfb..b8fbd78aa 100644
--- a/manifests/generated/operator-csv.yaml.in
+++ b/manifests/generated/operator-csv.yaml.in
@@ -1237,6 +1237,15 @@ spec:
       - rules:
         - apiGroups:
           - ""
+          resourceNames:
+          - kubevirt-ca
+          - kubevirt-export-ca
+          - kubevirt-virt-handler-certs
+          - kubevirt-virt-handler-server-certs
+          - kubevirt-operator-certs
+          - kubevirt-virt-api-certs
+          - kubevirt-controller-certs
+          - kubevirt-exportproxy-certs
           resources:
           - secrets
           verbs:
diff --git a/manifests/generated/rbac-operator.authorization.k8s.yaml.in b/manifests/generated/rbac-operator.authorization.k8s.yaml.in
index e066d5e9e..62db7e121 100644
--- a/manifests/generated/rbac-operator.authorization.k8s.yaml.in
+++ b/manifests/generated/rbac-operator.authorization.k8s.yaml.in
@@ -17,6 +17,15 @@ metadata:
 rules:
 - apiGroups:
   - ""
+  resourceNames:
+  - kubevirt-ca
+  - kubevirt-export-ca
+  - kubevirt-virt-handler-certs
+  - kubevirt-virt-handler-server-certs
+  - kubevirt-operator-certs
+  - kubevirt-virt-api-certs
+  - kubevirt-controller-certs
+  - kubevirt-exportproxy-certs
   resources:
   - secrets
   verbs:
diff --git a/pkg/virt-api/webhooks/BUILD.bazel b/pkg/virt-api/webhooks/BUILD.bazel
index b7ebdc8cb..8da9ed58e 100644
--- a/pkg/virt-api/webhooks/BUILD.bazel
+++ b/pkg/virt-api/webhooks/BUILD.bazel
@@ -12,7 +12,7 @@ go_library(
     visibility = ["//visibility:public"],
     deps = [
         "//pkg/virt-handler/node-labeller/util:go_default_library",
-        "//pkg/virt-operator/resource/generate/rbac:go_default_library",
+        "//pkg/virt-operator/resource/generate/components:go_default_library",
         "//staging/src/kubevirt.io/api/core/v1:go_default_library",
         "//staging/src/kubevirt.io/api/pool/v1alpha1:go_default_library",
         "//staging/src/kubevirt.io/client-go/log:go_default_library",
diff --git a/pkg/virt-api/webhooks/mutating-webhook/mutators/BUILD.bazel b/pkg/virt-api/webhooks/mutating-webhook/mutators/BUILD.bazel
index 06fe70e4f..85b50e86b 100644
--- a/pkg/virt-api/webhooks/mutating-webhook/mutators/BUILD.bazel
+++ b/pkg/virt-api/webhooks/mutating-webhook/mutators/BUILD.bazel
@@ -56,7 +56,7 @@ go_test(
         "//pkg/virt-api/webhooks:go_default_library",
         "//pkg/virt-config:go_default_library",
         "//pkg/virt-handler/node-labeller/util:go_default_library",
-        "//pkg/virt-operator/resource/generate/rbac:go_default_library",
+        "//pkg/virt-operator/resource/generate/components:go_default_library",
         "//staging/src/kubevirt.io/api/clone:go_default_library",
         "//staging/src/kubevirt.io/api/clone/v1alpha1:go_default_library",
         "//staging/src/kubevirt.io/api/core:go_default_library",
diff --git a/pkg/virt-api/webhooks/mutating-webhook/mutators/vmi-mutator_test.go b/pkg/virt-api/webhooks/mutating-webhook/mutators/vmi-mutator_test.go
index 16efbe35f..907967a45 100644
--- a/pkg/virt-api/webhooks/mutating-webhook/mutators/vmi-mutator_test.go
+++ b/pkg/virt-api/webhooks/mutating-webhook/mutators/vmi-mutator_test.go
@@ -46,10 +46,10 @@ import (
 	"kubevirt.io/kubevirt/pkg/virt-api/webhooks"
 	virtconfig "kubevirt.io/kubevirt/pkg/virt-config"
 	nodelabellerutil "kubevirt.io/kubevirt/pkg/virt-handler/node-labeller/util"
-	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/rbac"
+	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/components"
 )
 
-var privilegedUser = fmt.Sprintf("%s:%s:%s:%s", "system", "serviceaccount", "kubevirt", rbac.ControllerServiceAccountName)
+var privilegedUser = fmt.Sprintf("%s:%s:%s:%s", "system", "serviceaccount", "kubevirt", components.ControllerServiceAccountName)
 
 var _ = Describe("VirtualMachineInstance Mutator", func() {
 	var vmi *v1.VirtualMachineInstance
diff --git a/pkg/virt-api/webhooks/utils.go b/pkg/virt-api/webhooks/utils.go
index 948b2adcf..20a4a66bb 100644
--- a/pkg/virt-api/webhooks/utils.go
+++ b/pkg/virt-api/webhooks/utils.go
@@ -29,7 +29,7 @@ import (
 	poolv1 "kubevirt.io/api/pool/v1alpha1"
 	"kubevirt.io/client-go/log"
 
-	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/rbac"
+	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/components"
 
 	v1 "kubevirt.io/api/core/v1"
 	clientutil "kubevirt.io/client-go/util"
@@ -90,9 +90,9 @@ func IsKubeVirtServiceAccount(serviceAccount string) bool {
 	}
 
 	prefix := fmt.Sprintf("system:serviceaccount:%s", ns)
-	return serviceAccount == fmt.Sprintf("%s:%s", prefix, rbac.ApiServiceAccountName) ||
-		serviceAccount == fmt.Sprintf("%s:%s", prefix, rbac.HandlerServiceAccountName) ||
-		serviceAccount == fmt.Sprintf("%s:%s", prefix, rbac.ControllerServiceAccountName)
+	return serviceAccount == fmt.Sprintf("%s:%s", prefix, components.ApiServiceAccountName) ||
+		serviceAccount == fmt.Sprintf("%s:%s", prefix, components.HandlerServiceAccountName) ||
+		serviceAccount == fmt.Sprintf("%s:%s", prefix, components.ControllerServiceAccountName)
 }
 
 func IsARM64() bool {
diff --git a/pkg/virt-api/webhooks/validating-webhook/admitters/BUILD.bazel b/pkg/virt-api/webhooks/validating-webhook/admitters/BUILD.bazel
index 1654755ae..b73b4a3f1 100644
--- a/pkg/virt-api/webhooks/validating-webhook/admitters/BUILD.bazel
+++ b/pkg/virt-api/webhooks/validating-webhook/admitters/BUILD.bazel
@@ -98,7 +98,7 @@ go_test(
         "//pkg/virt-api/webhooks:go_default_library",
         "//pkg/virt-config:go_default_library",
         "//pkg/virt-handler/node-labeller/util:go_default_library",
-        "//pkg/virt-operator/resource/generate/rbac:go_default_library",
+        "//pkg/virt-operator/resource/generate/components:go_default_library",
         "//staging/src/kubevirt.io/api/clone:go_default_library",
         "//staging/src/kubevirt.io/api/clone/v1alpha1:go_default_library",
         "//staging/src/kubevirt.io/api/core:go_default_library",
diff --git a/pkg/virt-api/webhooks/validating-webhook/admitters/vmi-create-admitter_test.go b/pkg/virt-api/webhooks/validating-webhook/admitters/vmi-create-admitter_test.go
index d56a7493b..eff7c8b03 100644
--- a/pkg/virt-api/webhooks/validating-webhook/admitters/vmi-create-admitter_test.go
+++ b/pkg/virt-api/webhooks/validating-webhook/admitters/vmi-create-admitter_test.go
@@ -27,8 +27,6 @@ import (
 
 	"kubevirt.io/client-go/api"
 
-	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/rbac"
-
 	. "github.com/onsi/ginkgo/v2"
 	. "github.com/onsi/gomega"
 	admissionv1 "k8s.io/api/admission/v1"
@@ -49,6 +47,7 @@ import (
 	"kubevirt.io/kubevirt/pkg/virt-api/webhooks"
 	virtconfig "kubevirt.io/kubevirt/pkg/virt-config"
 	nodelabellerutil "kubevirt.io/kubevirt/pkg/virt-handler/node-labeller/util"
+	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/components"
 )
 
 var _ = Describe("Validating VMICreate Admitter", func() {
@@ -401,17 +400,17 @@ var _ = Describe("Validating VMICreate Admitter", func() {
 			},
 			Entry("Create restricted label by API",
 				map[string]string{v1.NodeNameLabel: "someValue"},
-				rbac.ApiServiceAccountName,
+				components.ApiServiceAccountName,
 				true,
 			),
 			Entry("Create restricted label by Handler",
 				map[string]string{v1.NodeNameLabel: "someValue"},
-				rbac.HandlerServiceAccountName,
+				components.HandlerServiceAccountName,
 				true,
 			),
 			Entry("Create restricted label by Controller",
 				map[string]string{v1.NodeNameLabel: "someValue"},
-				rbac.ControllerServiceAccountName,
+				components.ControllerServiceAccountName,
 				true,
 			),
 			Entry("Create restricted label by non kubevirt user",
diff --git a/pkg/virt-api/webhooks/validating-webhook/admitters/vmi-update-admitter_test.go b/pkg/virt-api/webhooks/validating-webhook/admitters/vmi-update-admitter_test.go
index 83a9d0390..a9f7af477 100644
--- a/pkg/virt-api/webhooks/validating-webhook/admitters/vmi-update-admitter_test.go
+++ b/pkg/virt-api/webhooks/validating-webhook/admitters/vmi-update-admitter_test.go
@@ -39,7 +39,7 @@ import (
 	"kubevirt.io/kubevirt/pkg/testutils"
 	webhookutils "kubevirt.io/kubevirt/pkg/util/webhooks"
 	"kubevirt.io/kubevirt/pkg/virt-api/webhooks"
-	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/rbac"
+	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/components"
 )
 
 var _ = Describe("Validating VMIUpdate Admitter", func() {
@@ -190,17 +190,17 @@ var _ = Describe("Validating VMIUpdate Admitter", func() {
 		Entry("Update by API",
 			map[string]string{v1.NodeNameLabel: "someValue"},
 			map[string]string{v1.NodeNameLabel: "someNewValue"},
-			rbac.ApiServiceAccountName,
+			components.ApiServiceAccountName,
 		),
 		Entry("Update by Handler",
 			map[string]string{v1.NodeNameLabel: "someValue"},
 			map[string]string{v1.NodeNameLabel: "someNewValue"},
-			rbac.HandlerServiceAccountName,
+			components.HandlerServiceAccountName,
 		),
 		Entry("Update by Controller",
 			map[string]string{v1.NodeNameLabel: "someValue"},
 			map[string]string{v1.NodeNameLabel: "someNewValue"},
-			rbac.ControllerServiceAccountName,
+			components.ControllerServiceAccountName,
 		),
 	)
 
@@ -560,7 +560,7 @@ var _ = Describe("Validating VMIUpdate Admitter", func() {
 		resp := vmiUpdateAdmitter.Admit(ar)
 		Expect(resp.Allowed).To(expected)
 	},
-		Entry("Should admit internal sa", "system:serviceaccount:kubevirt:"+rbac.ApiServiceAccountName, BeTrue()),
+		Entry("Should admit internal sa", "system:serviceaccount:kubevirt:"+components.ApiServiceAccountName, BeTrue()),
 		Entry("Should reject regular user", "system:serviceaccount:someNamespace:someUser", BeFalse()),
 	)
 })
diff --git a/pkg/virt-operator/resource/generate/components/BUILD.bazel b/pkg/virt-operator/resource/generate/components/BUILD.bazel
index 8a1b46b56..146c37a5f 100644
--- a/pkg/virt-operator/resource/generate/components/BUILD.bazel
+++ b/pkg/virt-operator/resource/generate/components/BUILD.bazel
@@ -11,6 +11,7 @@ go_library(
         "routes.go",
         "scc.go",
         "secrets.go",
+        "serviceaccountnames.go",
         "validations_generated.go",
         "webhooks.go",
     ],
@@ -21,7 +22,6 @@ go_library(
         "//pkg/certificates/triple:go_default_library",
         "//pkg/certificates/triple/cert:go_default_library",
         "//pkg/virt-config:go_default_library",
-        "//pkg/virt-operator/resource/generate/rbac:go_default_library",
         "//pkg/virt-operator/util:go_default_library",
         "//staging/src/kubevirt.io/api/clone:go_default_library",
         "//staging/src/kubevirt.io/api/clone/v1alpha1:go_default_library",
diff --git a/pkg/virt-operator/resource/generate/components/daemonsets.go b/pkg/virt-operator/resource/generate/components/daemonsets.go
index b6e9426d1..2a3c863f6 100644
--- a/pkg/virt-operator/resource/generate/components/daemonsets.go
+++ b/pkg/virt-operator/resource/generate/components/daemonsets.go
@@ -13,7 +13,6 @@ import (
 	virtv1 "kubevirt.io/api/core/v1"
 
 	virtconfig "kubevirt.io/kubevirt/pkg/virt-config"
-	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/rbac"
 	operatorutil "kubevirt.io/kubevirt/pkg/virt-operator/util"
 )
 
@@ -77,7 +76,7 @@ func NewHandlerDaemonSet(namespace string, repository string, imagePrefix string
 	}
 
 	pod := &daemonset.Spec.Template.Spec
-	pod.ServiceAccountName = rbac.HandlerServiceAccountName
+	pod.ServiceAccountName = HandlerServiceAccountName
 	pod.HostPID = true
 
 	// nodelabeller currently only support x86
diff --git a/pkg/virt-operator/resource/generate/components/deployments.go b/pkg/virt-operator/resource/generate/components/deployments.go
index 9af531287..a64476bb8 100644
--- a/pkg/virt-operator/resource/generate/components/deployments.go
+++ b/pkg/virt-operator/resource/generate/components/deployments.go
@@ -34,7 +34,6 @@ import (
 
 	virtv1 "kubevirt.io/api/core/v1"
 
-	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/rbac"
 	operatorutil "kubevirt.io/kubevirt/pkg/virt-operator/util"
 )
 
@@ -318,7 +317,7 @@ func NewApiServerDeployment(namespace string, repository string, imagePrefix str
 	attachProfileVolume(&deployment.Spec.Template.Spec)
 
 	pod := &deployment.Spec.Template.Spec
-	pod.ServiceAccountName = rbac.ApiServiceAccountName
+	pod.ServiceAccountName = ApiServiceAccountName
 	pod.SecurityContext = &corev1.PodSecurityContext{
 		RunAsNonRoot:   boolPtr(true),
 		SeccompProfile: &corev1.SeccompProfile{Type: corev1.SeccompProfileTypeRuntimeDefault},
@@ -392,7 +391,7 @@ func NewControllerDeployment(namespace string, repository string, imagePrefix st
 	}
 
 	pod := &deployment.Spec.Template.Spec
-	pod.ServiceAccountName = rbac.ControllerServiceAccountName
+	pod.ServiceAccountName = ControllerServiceAccountName
 	pod.SecurityContext = &corev1.PodSecurityContext{
 		RunAsNonRoot:   boolPtr(true),
 		SeccompProfile: &corev1.SeccompProfile{Type: corev1.SeccompProfileTypeRuntimeDefault},
@@ -663,7 +662,7 @@ func NewExportProxyDeployment(namespace string, repository string, imagePrefix s
 	attachProfileVolume(&deployment.Spec.Template.Spec)
 
 	pod := &deployment.Spec.Template.Spec
-	pod.ServiceAccountName = rbac.ExportProxyServiceAccountName
+	pod.ServiceAccountName = ExportProxyServiceAccountName
 	pod.SecurityContext = &corev1.PodSecurityContext{
 		RunAsNonRoot: boolPtr(true),
 	}
diff --git a/pkg/virt-operator/resource/generate/components/serviceaccountnames.go b/pkg/virt-operator/resource/generate/components/serviceaccountnames.go
new file mode 100644
index 000000000..0948629bb
--- /dev/null
+++ b/pkg/virt-operator/resource/generate/components/serviceaccountnames.go
@@ -0,0 +1,9 @@
+package components
+
+const (
+	ApiServiceAccountName         = "kubevirt-apiserver"
+	ControllerServiceAccountName  = "kubevirt-controller"
+	ExportProxyServiceAccountName = "kubevirt-exportproxy"
+	HandlerServiceAccountName     = "kubevirt-handler"
+	OperatorServiceAccountName    = "kubevirt-operator"
+)
diff --git a/pkg/virt-operator/resource/generate/rbac/BUILD.bazel b/pkg/virt-operator/resource/generate/rbac/BUILD.bazel
index fb3952f7b..8de09055f 100644
--- a/pkg/virt-operator/resource/generate/rbac/BUILD.bazel
+++ b/pkg/virt-operator/resource/generate/rbac/BUILD.bazel
@@ -14,6 +14,7 @@ go_library(
     importpath = "kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/rbac",
     visibility = ["//visibility:public"],
     deps = [
+        "//pkg/virt-operator/resource/generate/components:go_default_library",
         "//staging/src/kubevirt.io/api/clone:go_default_library",
         "//staging/src/kubevirt.io/api/core/v1:go_default_library",
         "//staging/src/kubevirt.io/api/instancetype:go_default_library",
@@ -33,6 +34,7 @@ go_test(
     ],
     embed = [":go_default_library"],
     deps = [
+        "//pkg/virt-operator/resource/generate/components:go_default_library",
         "//staging/src/kubevirt.io/client-go/testutils:go_default_library",
         "//vendor/github.com/onsi/ginkgo/v2:go_default_library",
         "//vendor/github.com/onsi/gomega:go_default_library",
diff --git a/pkg/virt-operator/resource/generate/rbac/apiserver.go b/pkg/virt-operator/resource/generate/rbac/apiserver.go
index 43f7d5647..5b77ce4bd 100644
--- a/pkg/virt-operator/resource/generate/rbac/apiserver.go
+++ b/pkg/virt-operator/resource/generate/rbac/apiserver.go
@@ -26,6 +26,8 @@ import (
 
 	"kubevirt.io/api/instancetype"
 
+	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/components"
+
 	virtv1 "kubevirt.io/api/core/v1"
 	"kubevirt.io/api/migrations"
 )
@@ -36,8 +38,6 @@ const (
 	GroupName     = "kubevirt.io"
 )
 
-const ApiServiceAccountName = "kubevirt-apiserver"
-
 func GetAllApiServer(namespace string) []runtime.Object {
 	return []runtime.Object{
 		newApiServerServiceAccount(namespace),
@@ -57,7 +57,7 @@ func newApiServerServiceAccount(namespace string) *corev1.ServiceAccount {
 		},
 		ObjectMeta: metav1.ObjectMeta{
 			Namespace: namespace,
-			Name:      ApiServiceAccountName,
+			Name:      components.ApiServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -72,7 +72,7 @@ func newApiServerClusterRole() *rbacv1.ClusterRole {
 			Kind:       "ClusterRole",
 		},
 		ObjectMeta: metav1.ObjectMeta{
-			Name: ApiServiceAccountName,
+			Name: components.ApiServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -265,7 +265,7 @@ func newApiServerClusterRoleBinding(namespace string) *rbacv1.ClusterRoleBinding
 			Kind:       "ClusterRoleBinding",
 		},
 		ObjectMeta: metav1.ObjectMeta{
-			Name: ApiServiceAccountName,
+			Name: components.ApiServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -273,13 +273,13 @@ func newApiServerClusterRoleBinding(namespace string) *rbacv1.ClusterRoleBinding
 		RoleRef: rbacv1.RoleRef{
 			APIGroup: VersionName,
 			Kind:     "ClusterRole",
-			Name:     ApiServiceAccountName,
+			Name:     components.ApiServiceAccountName,
 		},
 		Subjects: []rbacv1.Subject{
 			{
 				Kind:      "ServiceAccount",
 				Namespace: namespace,
-				Name:      ApiServiceAccountName,
+				Name:      components.ApiServiceAccountName,
 			},
 		},
 	}
@@ -306,7 +306,7 @@ func newApiServerAuthDelegatorClusterRoleBinding(namespace string) *rbacv1.Clust
 			{
 				Kind:      "ServiceAccount",
 				Namespace: namespace,
-				Name:      ApiServiceAccountName,
+				Name:      components.ApiServiceAccountName,
 			},
 		},
 	}
@@ -320,7 +320,7 @@ func newApiServerRole(namespace string) *rbacv1.Role {
 		},
 		ObjectMeta: metav1.ObjectMeta{
 			Namespace: namespace,
-			Name:      ApiServiceAccountName,
+			Name:      components.ApiServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -349,7 +349,7 @@ func newApiServerRoleBinding(namespace string) *rbacv1.RoleBinding {
 		},
 		ObjectMeta: metav1.ObjectMeta{
 			Namespace: namespace,
-			Name:      ApiServiceAccountName,
+			Name:      components.ApiServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -357,13 +357,13 @@ func newApiServerRoleBinding(namespace string) *rbacv1.RoleBinding {
 		RoleRef: rbacv1.RoleRef{
 			APIGroup: VersionName,
 			Kind:     "Role",
-			Name:     ApiServiceAccountName,
+			Name:     components.ApiServiceAccountName,
 		},
 		Subjects: []rbacv1.Subject{
 			{
 				Kind:      "ServiceAccount",
 				Namespace: namespace,
-				Name:      ApiServiceAccountName,
+				Name:      components.ApiServiceAccountName,
 			},
 		},
 	}
diff --git a/pkg/virt-operator/resource/generate/rbac/controller.go b/pkg/virt-operator/resource/generate/rbac/controller.go
index 8da9f0a5d..3ebe9c1aa 100644
--- a/pkg/virt-operator/resource/generate/rbac/controller.go
+++ b/pkg/virt-operator/resource/generate/rbac/controller.go
@@ -26,14 +26,14 @@ import (
 
 	"kubevirt.io/api/clone"
 
+	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/components"
+
 	"kubevirt.io/api/instancetype"
 
 	virtv1 "kubevirt.io/api/core/v1"
 	"kubevirt.io/api/migrations"
 )
 
-const ControllerServiceAccountName = "kubevirt-controller"
-
 func GetAllController(namespace string) []runtime.Object {
 	return []runtime.Object{
 		newControllerServiceAccount(namespace),
@@ -52,7 +52,7 @@ func newControllerServiceAccount(namespace string) *corev1.ServiceAccount {
 		},
 		ObjectMeta: metav1.ObjectMeta{
 			Namespace: namespace,
-			Name:      ControllerServiceAccountName,
+			Name:      components.ControllerServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -67,7 +67,7 @@ func newControllerRole(namespace string) *rbacv1.Role {
 			Kind:       "Role",
 		},
 		ObjectMeta: metav1.ObjectMeta{
-			Name:      ControllerServiceAccountName,
+			Name:      components.ControllerServiceAccountName,
 			Namespace: namespace,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
@@ -124,7 +124,7 @@ func newControllerRoleBinding(namespace string) *rbacv1.RoleBinding {
 			Kind:       "RoleBinding",
 		},
 		ObjectMeta: metav1.ObjectMeta{
-			Name:      ControllerServiceAccountName,
+			Name:      components.ControllerServiceAccountName,
 			Namespace: namespace,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
@@ -133,13 +133,13 @@ func newControllerRoleBinding(namespace string) *rbacv1.RoleBinding {
 		RoleRef: rbacv1.RoleRef{
 			APIGroup: VersionName,
 			Kind:     "Role",
-			Name:     ControllerServiceAccountName,
+			Name:     components.ControllerServiceAccountName,
 		},
 		Subjects: []rbacv1.Subject{
 			{
 				Kind:      "ServiceAccount",
 				Namespace: namespace,
-				Name:      ControllerServiceAccountName,
+				Name:      components.ControllerServiceAccountName,
 			},
 		},
 	}
@@ -152,7 +152,7 @@ func newControllerClusterRole() *rbacv1.ClusterRole {
 			Kind:       "ClusterRole",
 		},
 		ObjectMeta: metav1.ObjectMeta{
-			Name: ControllerServiceAccountName,
+			Name: components.ControllerServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -512,7 +512,7 @@ func newControllerClusterRoleBinding(namespace string) *rbacv1.ClusterRoleBindin
 			Kind:       "ClusterRoleBinding",
 		},
 		ObjectMeta: metav1.ObjectMeta{
-			Name: ControllerServiceAccountName,
+			Name: components.ControllerServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -520,13 +520,13 @@ func newControllerClusterRoleBinding(namespace string) *rbacv1.ClusterRoleBindin
 		RoleRef: rbacv1.RoleRef{
 			APIGroup: "rbac.authorization.k8s.io",
 			Kind:     "ClusterRole",
-			Name:     ControllerServiceAccountName,
+			Name:     components.ControllerServiceAccountName,
 		},
 		Subjects: []rbacv1.Subject{
 			{
 				Kind:      "ServiceAccount",
 				Namespace: namespace,
-				Name:      ControllerServiceAccountName,
+				Name:      components.ControllerServiceAccountName,
 			},
 		},
 	}
diff --git a/pkg/virt-operator/resource/generate/rbac/handler.go b/pkg/virt-operator/resource/generate/rbac/handler.go
index c47adc28a..e55a4044e 100644
--- a/pkg/virt-operator/resource/generate/rbac/handler.go
+++ b/pkg/virt-operator/resource/generate/rbac/handler.go
@@ -27,9 +27,9 @@ import (
 
 	virtv1 "kubevirt.io/api/core/v1"
 	"kubevirt.io/api/migrations"
-)
 
-const HandlerServiceAccountName = "kubevirt-handler"
+	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/components"
+)
 
 func GetAllHandler(namespace string) []runtime.Object {
 	return []runtime.Object{
@@ -49,7 +49,7 @@ func newHandlerServiceAccount(namespace string) *corev1.ServiceAccount {
 		},
 		ObjectMeta: metav1.ObjectMeta{
 			Namespace: namespace,
-			Name:      HandlerServiceAccountName,
+			Name:      components.HandlerServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -64,7 +64,7 @@ func newHandlerClusterRole() *rbacv1.ClusterRole {
 			Kind:       "ClusterRole",
 		},
 		ObjectMeta: metav1.ObjectMeta{
-			Name: HandlerServiceAccountName,
+			Name: components.HandlerServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -167,7 +167,7 @@ func newHandlerClusterRoleBinding(namespace string) *rbacv1.ClusterRoleBinding {
 			Kind:       "ClusterRoleBinding",
 		},
 		ObjectMeta: metav1.ObjectMeta{
-			Name: HandlerServiceAccountName,
+			Name: components.HandlerServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -175,13 +175,13 @@ func newHandlerClusterRoleBinding(namespace string) *rbacv1.ClusterRoleBinding {
 		RoleRef: rbacv1.RoleRef{
 			APIGroup: "rbac.authorization.k8s.io",
 			Kind:     "ClusterRole",
-			Name:     HandlerServiceAccountName,
+			Name:     components.HandlerServiceAccountName,
 		},
 		Subjects: []rbacv1.Subject{
 			{
 				Kind:      "ServiceAccount",
 				Namespace: namespace,
-				Name:      HandlerServiceAccountName,
+				Name:      components.HandlerServiceAccountName,
 			},
 		},
 	}
@@ -195,7 +195,7 @@ func newHandlerRole(namespace string) *rbacv1.Role {
 		},
 		ObjectMeta: metav1.ObjectMeta{
 			Namespace: namespace,
-			Name:      HandlerServiceAccountName,
+			Name:      components.HandlerServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -224,7 +224,7 @@ func newHandlerRoleBinding(namespace string) *rbacv1.RoleBinding {
 		},
 		ObjectMeta: metav1.ObjectMeta{
 			Namespace: namespace,
-			Name:      HandlerServiceAccountName,
+			Name:      components.HandlerServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -232,13 +232,13 @@ func newHandlerRoleBinding(namespace string) *rbacv1.RoleBinding {
 		RoleRef: rbacv1.RoleRef{
 			APIGroup: "rbac.authorization.k8s.io",
 			Kind:     "Role",
-			Name:     HandlerServiceAccountName,
+			Name:     components.HandlerServiceAccountName,
 		},
 		Subjects: []rbacv1.Subject{
 			{
 				Kind:      "ServiceAccount",
 				Namespace: namespace,
-				Name:      HandlerServiceAccountName,
+				Name:      components.HandlerServiceAccountName,
 			},
 		},
 	}
diff --git a/pkg/virt-operator/resource/generate/rbac/operator.go b/pkg/virt-operator/resource/generate/rbac/operator.go
index 29ec8c85a..f15dfa554 100644
--- a/pkg/virt-operator/resource/generate/rbac/operator.go
+++ b/pkg/virt-operator/resource/generate/rbac/operator.go
@@ -26,6 +26,8 @@ import (
 	metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
 
 	virtv1 "kubevirt.io/api/core/v1"
+
+	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/components"
 )
 
 const (
@@ -33,7 +35,6 @@ const (
 	GroupNameRoute    = "route.openshift.io"
 	serviceAccountFmt = "%s:%s:%s"
 )
-const OperatorServiceAccountName = "kubevirt-operator"
 
 // Used for manifest generation only, not by the operator itself
 func GetAllOperator(namespace string) []interface{} {
@@ -54,7 +55,7 @@ func newOperatorServiceAccount(namespace string) *corev1.ServiceAccount {
 		},
 		ObjectMeta: metav1.ObjectMeta{
 			Namespace: namespace,
-			Name:      OperatorServiceAccountName,
+			Name:      components.OperatorServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -74,7 +75,7 @@ func NewOperatorClusterRole() *rbacv1.ClusterRole {
 			Kind:       "ClusterRole",
 		},
 		ObjectMeta: metav1.ObjectMeta{
-			Name: OperatorServiceAccountName,
+			Name: components.OperatorServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -396,7 +397,7 @@ func newOperatorClusterRoleBinding(namespace string) *rbacv1.ClusterRoleBinding
 			Kind:       "ClusterRoleBinding",
 		},
 		ObjectMeta: metav1.ObjectMeta{
-			Name: OperatorServiceAccountName,
+			Name: components.OperatorServiceAccountName,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
 			},
@@ -404,13 +405,13 @@ func newOperatorClusterRoleBinding(namespace string) *rbacv1.ClusterRoleBinding
 		RoleRef: rbacv1.RoleRef{
 			APIGroup: VersionName,
 			Kind:     "ClusterRole",
-			Name:     OperatorServiceAccountName,
+			Name:     components.OperatorServiceAccountName,
 		},
 		Subjects: []rbacv1.Subject{
 			{
 				Kind:      "ServiceAccount",
 				Namespace: namespace,
-				Name:      OperatorServiceAccountName,
+				Name:      components.OperatorServiceAccountName,
 			},
 		},
 	}
@@ -432,13 +433,13 @@ func newOperatorRoleBinding(namespace string) *rbacv1.RoleBinding {
 		RoleRef: rbacv1.RoleRef{
 			APIGroup: VersionName,
 			Kind:     "Role",
-			Name:     OperatorServiceAccountName,
+			Name:     components.OperatorServiceAccountName,
 		},
 		Subjects: []rbacv1.Subject{
 			{
 				Kind:      "ServiceAccount",
 				Namespace: namespace,
-				Name:      OperatorServiceAccountName,
+				Name:      components.OperatorServiceAccountName,
 			},
 		},
 	}
@@ -452,7 +453,7 @@ func NewOperatorRole(namespace string) *rbacv1.Role {
 			Kind:       "Role",
 		},
 		ObjectMeta: metav1.ObjectMeta{
-			Name:      OperatorServiceAccountName,
+			Name:      components.OperatorServiceAccountName,
 			Namespace: namespace,
 			Labels: map[string]string{
 				virtv1.AppLabel: "",
@@ -466,6 +467,16 @@ func NewOperatorRole(namespace string) *rbacv1.Role {
 				Resources: []string{
 					"secrets",
 				},
+				ResourceNames: []string{
+					components.KubeVirtCASecretName,
+					components.KubeVirtExportCASecretName,
+					components.VirtHandlerCertSecretName,
+					components.VirtHandlerServerCertSecretName,
+					components.VirtOperatorCertSecretName,
+					components.VirtApiCertSecretName,
+					components.VirtControllerCertSecretName,
+					components.VirtExportProxyCertSecretName,
+				},
 				Verbs: []string{
 					"create",
 					"get",
@@ -526,10 +537,10 @@ func GetKubevirtComponentsServiceAccounts(namespace string) map[string]bool {
 	usermap := make(map[string]bool)
 
 	prefix := "system:serviceaccount"
-	usermap[fmt.Sprintf(serviceAccountFmt, prefix, namespace, HandlerServiceAccountName)] = true
-	usermap[fmt.Sprintf(serviceAccountFmt, prefix, namespace, ApiServiceAccountName)] = true
-	usermap[fmt.Sprintf(serviceAccountFmt, prefix, namespace, ControllerServiceAccountName)] = true
-	usermap[fmt.Sprintf(serviceAccountFmt, prefix, namespace, OperatorServiceAccountName)] = true
+	usermap[fmt.Sprintf(serviceAccountFmt, prefix, namespace, components.HandlerServiceAccountName)] = true
+	usermap[fmt.Sprintf(serviceAccountFmt, prefix, namespace, components.ApiServiceAccountName)] = true
+	usermap[fmt.Sprintf(serviceAccountFmt, prefix, namespace, components.ControllerServiceAccountName)] = true
+	usermap[fmt.Sprintf(serviceAccountFmt, prefix, namespace, components.OperatorServiceAccountName)] = true
 
 	return usermap
 }
diff --git a/pkg/virt-operator/resource/generate/rbac/operator_test.go b/pkg/virt-operator/resource/generate/rbac/operator_test.go
index 701a8c4f5..51bd479cc 100644
--- a/pkg/virt-operator/resource/generate/rbac/operator_test.go
+++ b/pkg/virt-operator/resource/generate/rbac/operator_test.go
@@ -26,6 +26,8 @@ import (
 	. "github.com/onsi/gomega"
 	v1 "k8s.io/api/core/v1"
 	rbacv1 "k8s.io/api/rbac/v1"
+
+	"kubevirt.io/kubevirt/pkg/virt-operator/resource/generate/components"
 )
 
 var _ = Describe("RBAC", func() {
@@ -75,10 +77,10 @@ var _ = Describe("RBAC", func() {
 			func(name string) {
 				Expect(serviceAccounts).To(HaveKey(MatchRegexp(fmt.Sprintf(".*%s.*", name))))
 			},
-			Entry("for Handler", HandlerServiceAccountName),
-			Entry("for Api", ApiServiceAccountName),
-			Entry("for Controller", ControllerServiceAccountName),
-			Entry("for Operator", OperatorServiceAccountName),
+			Entry("for Handler", components.HandlerServiceAccountName),
+			Entry("for Api", components.ApiServiceAccountName),
+			Entry("for Controller", components.ControllerServiceAccountName),
+			Entry("for Operator", components.OperatorServiceAccountName),
 		)
 
 	})
-- 
2.39.2

