diff --git a/UPSTREAM_PROJECTS.yaml b/UPSTREAM_PROJECTS.yaml index 793be61d0b..760f8a8e07 100644 --- a/UPSTREAM_PROJECTS.yaml +++ b/UPSTREAM_PROJECTS.yaml @@ -181,8 +181,8 @@ projects: repos: - name: cluster-api versions: - - tag: v1.6.1 - go_version: "1.20" + - tag: v1.6.3 + go_version: "1.21" - name: cluster-api-provider-cloudstack versions: - tag: v0.4.10-rc1 diff --git a/projects/kubernetes-sigs/cluster-api/ATTRIBUTION.txt b/projects/kubernetes-sigs/cluster-api/ATTRIBUTION.txt index 54247b48d5..57072f1280 100644 --- a/projects/kubernetes-sigs/cluster-api/ATTRIBUTION.txt +++ b/projects/kubernetes-sigs/cluster-api/ATTRIBUTION.txt @@ -227,7 +227,7 @@ https://github.com/kubernetes/utils ** sigs.k8s.io/apiserver-network-proxy/konnectivity-client; version v0.1.2 -- https://github.com/kubernetes-sigs/apiserver-network-proxy -** sigs.k8s.io/cluster-api; version v1.6.1 -- +** sigs.k8s.io/cluster-api; version v1.6.3 -- https://github.com/kubernetes-sigs/cluster-api ** sigs.k8s.io/controller-runtime; version v0.16.5-0.20240215143111-dca5e8b2b00a -- @@ -1201,7 +1201,7 @@ https://github.com/ProtonMail/go-crypto ** github.com/sagikazarmark/slog-shim; version v0.1.0 -- https://github.com/sagikazarmark/slog-shim -** golang.org/go; version go1.20.14 -- +** golang.org/go; version go1.21.8 -- https://github.com/golang/go ** golang.org/x/crypto; version v0.17.0 -- @@ -1444,7 +1444,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ------ -** google.golang.org/protobuf; version v1.31.0 -- +** google.golang.org/protobuf; version v1.33.0 -- https://go.googlesource.com/protobuf Copyright (c) 2018 The Go Authors. All rights reserved. diff --git a/projects/kubernetes-sigs/cluster-api/CAPD_ATTRIBUTION.txt b/projects/kubernetes-sigs/cluster-api/CAPD_ATTRIBUTION.txt index a9de967627..4b37c7ccaf 100644 --- a/projects/kubernetes-sigs/cluster-api/CAPD_ATTRIBUTION.txt +++ b/projects/kubernetes-sigs/cluster-api/CAPD_ATTRIBUTION.txt @@ -191,13 +191,13 @@ https://github.com/kubernetes-sigs/apiserver-network-proxy ** sigs.k8s.io/cluster-api; version v0.0.0-00010101000000-000000000000 -- https://github.com/kubernetes-sigs/cluster-api -** sigs.k8s.io/cluster-api/test/infrastructure/container; version v1.6.1 -- +** sigs.k8s.io/cluster-api/test/infrastructure/container; version v1.6.3 -- https://github.com/kubernetes-sigs/cluster-api -** sigs.k8s.io/cluster-api/test/infrastructure/docker; version v1.6.1 -- +** sigs.k8s.io/cluster-api/test/infrastructure/docker; version v1.6.3 -- https://github.com/kubernetes-sigs/cluster-api -** sigs.k8s.io/cluster-api/test/infrastructure/kind; version v1.6.1 -- +** sigs.k8s.io/cluster-api/test/infrastructure/kind; version v1.6.3 -- https://github.com/kubernetes-sigs/cluster-api ** sigs.k8s.io/controller-runtime; version v0.16.5-0.20240215143111-dca5e8b2b00a -- @@ -1006,7 +1006,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ------ -** golang.org/go; version go1.20.14 -- +** golang.org/go; version go1.21.8 -- https://github.com/golang/go ** golang.org/x/crypto; version v0.17.0 -- @@ -1069,7 +1069,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ------ -** google.golang.org/protobuf; version v1.31.0 -- +** google.golang.org/protobuf; version v1.33.0 -- https://go.googlesource.com/protobuf Copyright (c) 2018 The Go Authors. All rights reserved. diff --git a/projects/kubernetes-sigs/cluster-api/CHECKSUMS b/projects/kubernetes-sigs/cluster-api/CHECKSUMS index e90487f5bd..764fa6a856 100644 --- a/projects/kubernetes-sigs/cluster-api/CHECKSUMS +++ b/projects/kubernetes-sigs/cluster-api/CHECKSUMS @@ -1,10 +1,10 @@ -da644118e346d1302527f73d3d60767333cb2124c7506d60e003bc8b6c02a641 _output/bin/cluster-api/linux-amd64/cluster-api-provider-docker-manager -3c3a86fd04d4aba3bc48213b74c46715de9a6f506ddce864719f7ce7c9fb0101 _output/bin/cluster-api/linux-amd64/clusterctl -dd5fff40cbe8b9a60ee95ed47b2c9e765c97d11bf1edde9af2776b0e94b62ffd _output/bin/cluster-api/linux-amd64/kubeadm-bootstrap-manager -b9b823229452f7f6d4100acfca49c9da04d20185b8b81f220a13da56840e2105 _output/bin/cluster-api/linux-amd64/kubeadm-control-plane-manager -7c3f7221ccfb9d59c4830d8de9eddccd56339889bd94df5d98710a20f048eca1 _output/bin/cluster-api/linux-amd64/manager -9da0f07c30b35dcb39f1ff8890bac67c58edaadd8a0f2dbdbc9a55839a92193b _output/bin/cluster-api/linux-arm64/cluster-api-provider-docker-manager -dfb3c46a6cab46413cc8169ca7e19904cbca7dcbca841603deaac394bb307693 _output/bin/cluster-api/linux-arm64/clusterctl -d691a73c22135527a5704369aa9682afae9d15154564cc20b2d0f30d9f39ef4a _output/bin/cluster-api/linux-arm64/kubeadm-bootstrap-manager -e0b535174a1cdea41f22c4e17ae8e7418155832f44dce03d0a883b272abc7ccb _output/bin/cluster-api/linux-arm64/kubeadm-control-plane-manager -8c73065301a79e51369a5d477510cc9fb3cf0d29ae58efdac259b0b363c68acc _output/bin/cluster-api/linux-arm64/manager +2cb4698f4f5948fd844f2b20f0f01b8b8cdf2525f474f9e5b90db60cc51b3ecc _output/bin/cluster-api/linux-amd64/cluster-api-provider-docker-manager +0fc69bdb40acf226c8ec7b4c08af14007e74dbbea190b973a552930d84de96d7 _output/bin/cluster-api/linux-amd64/clusterctl +9b7be46bf0bd5bef17b21c943f5fb93ed048d36317124c01fb12085e14980fbc _output/bin/cluster-api/linux-amd64/kubeadm-bootstrap-manager +400dde84a6056bb418c37a20da0313524745407d2ca334728ceea3a108aa14df _output/bin/cluster-api/linux-amd64/kubeadm-control-plane-manager +bd0ef3615c6c7798916623004ca380e543f1e15eb572143690992a4d9c2eddf9 _output/bin/cluster-api/linux-amd64/manager +64e96b486f9891cd95723f16ae180a461ee47dd8a09c0d00be8a05b8d8f83eb6 _output/bin/cluster-api/linux-arm64/cluster-api-provider-docker-manager +79f11cf152e6085993d08b388ea9c5dffb002a38b37e9274c481db73f4317750 _output/bin/cluster-api/linux-arm64/clusterctl +fc3d2fae9df645e3e9c2c952933e2f4d2e3b3a52ac6a5c24ccd4ee3565c1afc5 _output/bin/cluster-api/linux-arm64/kubeadm-bootstrap-manager +f9bfbbb7102662ad93061c146ff459db07045eba77e0f157e8d8bb8f35877e5e _output/bin/cluster-api/linux-arm64/kubeadm-control-plane-manager +bec2152de3fa9f8783c2121e9d573cd587963faf69126864b40ef329c7e38257 _output/bin/cluster-api/linux-arm64/manager diff --git a/projects/kubernetes-sigs/cluster-api/GIT_TAG b/projects/kubernetes-sigs/cluster-api/GIT_TAG index 0236045093..78d19a2970 100644 --- a/projects/kubernetes-sigs/cluster-api/GIT_TAG +++ b/projects/kubernetes-sigs/cluster-api/GIT_TAG @@ -1 +1 @@ -v1.6.1 +v1.6.3 diff --git a/projects/kubernetes-sigs/cluster-api/GOLANG_VERSION b/projects/kubernetes-sigs/cluster-api/GOLANG_VERSION index 5fb5a6b4f5..d2ab029d32 100644 --- a/projects/kubernetes-sigs/cluster-api/GOLANG_VERSION +++ b/projects/kubernetes-sigs/cluster-api/GOLANG_VERSION @@ -1 +1 @@ -1.20 +1.21 diff --git a/projects/kubernetes-sigs/cluster-api/README.md b/projects/kubernetes-sigs/cluster-api/README.md index a328d98922..ea8de00a2e 100644 --- a/projects/kubernetes-sigs/cluster-api/README.md +++ b/projects/kubernetes-sigs/cluster-api/README.md @@ -1,5 +1,5 @@ ## **Cluster API** -![Version](https://img.shields.io/badge/version-v1.6.1-blue) +![Version](https://img.shields.io/badge/version-v1.6.3-blue) ![Build Status](https://codebuild.us-west-2.amazonaws.com/badges?uuid=eyJlbmNyeXB0ZWREYXRhIjoiQVZ3TDBZZVVXZUZiVmtqLzVoOVcrV2FaMmxRRzJXRmJCRlZtQkNodXdWZ0FrNm0zQ3l5UzNqTkdsQXgwdzc0bTBZc1RIcjBhMUVFbEhIK3d2VDVPek1rPSIsIml2UGFyYW1ldGVyU3BlYyI6IkVuOGJxNXBPZEtDek81Q3giLCJtYXRlcmlhbFNldFNlcmlhbCI6MX0%3D&branch=main) [Cluster API](https://github.com/kubernetes-sigs/cluster-api) is a Kubernetes sub-project focused on providing declarative APIs and tooling to simplify provisioning, upgrading, and operating multiple Kubernetes clusters. It uses Kubernetes-style APIs and patterns to automate cluster lifecycle management for platform operators. The supporting infrastructure, like virtual machines, networks, load balancers, and VPCs, as well as the Kubernetes cluster configuration are all defined in the same way that application developers operate deploying and managing their workloads. This enables consistent and repeatable cluster deployments across a wide variety of infrastructure environments. Cluster API can be extended to support any infrastructure provider (AWS, Azure, vSphere, etc.) or bootstrap provider (kubeadm is default) as required by the customer. diff --git a/projects/kubernetes-sigs/cluster-api/patches/0001-Adding-capi-support-for-Bottlerocket.patch b/projects/kubernetes-sigs/cluster-api/patches/0001-Adding-capi-support-for-Bottlerocket.patch index 335b1d62e4..6395012b83 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0001-Adding-capi-support-for-Bottlerocket.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0001-Adding-capi-support-for-Bottlerocket.patch @@ -1,4 +1,4 @@ -From 2f93c9f85a68de6a65fdb3515f406108b85b77c1 Mon Sep 17 00:00:00 2001 +From 31769793dab5cc07b2fba520e998f15d203854e0 Mon Sep 17 00:00:00 2001 From: Vignesh Goutham Ganesh Date: Fri, 11 Jun 2021 10:43:09 -0700 Subject: [PATCH 01/40] Adding capi support for Bottlerocket @@ -29,6 +29,7 @@ Add network settings only when there is a proxy defined Remove userdata logging for bottlerocket --- + Makefile | 3 +- .../kubeadm/api/v1beta1/kubeadm_types.go | 53 +++++ .../api/v1beta1/kubeadmconfig_types.go | 5 +- ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 174 ++++++++++++++++ @@ -44,9 +45,10 @@ Remove userdata logging for bottlerocket .../kubeadm/internal/bottlerocket/utils.go | 18 ++ .../kubeadm/internal/cloudinit/cloudinit.go | 2 +- .../controllers/kubeadmconfig_controller.go | 73 +++++++ + .../kubeadm/types/upstreamv1beta1/types.go | 53 +++++ ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 186 ++++++++++++++++++ ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 99 ++++++++++ - 17 files changed, 1295 insertions(+), 2 deletions(-) + 19 files changed, 1350 insertions(+), 3 deletions(-) create mode 100644 bootstrap/kubeadm/internal/bottlerocket/bootstrap.go create mode 100644 bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go create mode 100644 bootstrap/kubeadm/internal/bottlerocket/bottlerocket_test.go @@ -57,6 +59,21 @@ Remove userdata logging for bottlerocket create mode 100644 bootstrap/kubeadm/internal/bottlerocket/users.go create mode 100644 bootstrap/kubeadm/internal/bottlerocket/utils.go +diff --git a/Makefile b/Makefile +index b5fb87d77..dc37c436b 100644 +--- a/Makefile ++++ b/Makefile +@@ -493,8 +493,9 @@ generate-go-conversions-kubeadm-bootstrap: $(CONVERSION_GEN) ## Generate convers + --extra-peer-dirs=sigs.k8s.io/cluster-api/api/v1alpha4 \ + --output-file-base=zz_generated.conversion $(CONVERSION_GEN_OUTPUT_BASE) \ + --go-header-file=./hack/boilerplate/boilerplate.generatego.txt +- $(MAKE) clean-generated-conversions SRC_DIRS="./bootstrap/kubeadm/types/upstreamv1beta2,./bootstrap/kubeadm/types/upstreamv1beta3" ++ $(MAKE) clean-generated-conversions SRC_DIRS="./bootstrap/kubeadm/types/upstreamv1beta1,./bootstrap/kubeadm/types/upstreamv1beta2,./bootstrap/kubeadm/types/upstreamv1beta3" + $(CONVERSION_GEN) \ ++ --input-dirs=./bootstrap/kubeadm/types/upstreamv1beta1 \ + --input-dirs=./bootstrap/kubeadm/types/upstreamv1beta2 \ + --input-dirs=./bootstrap/kubeadm/types/upstreamv1beta3 \ + --build-tag=ignore_autogenerated_kubeadm_types \ diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go index 653b4da55..11aa737a7 100644 --- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go @@ -159,10 +176,10 @@ index 70b9c133b..d68d247c7 100644 var ( diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -index 609887790..12ccced93 100644 +index 8c29323a0..e2ebd6fb6 100644 --- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -@@ -108,6 +108,21 @@ spec: +@@ -103,6 +103,21 @@ spec: schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -184,7 +201,7 @@ index 609887790..12ccced93 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, this will -@@ -308,6 +323,34 @@ spec: +@@ -306,6 +321,34 @@ spec: if that's unset. type: string type: object @@ -219,7 +236,7 @@ index 609887790..12ccced93 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -492,6 +535,7 @@ spec: +@@ -495,6 +538,7 @@ spec: description: Format specifies the output format of the bootstrap data enum: - cloud-config @@ -249,7 +266,7 @@ index 609887790..12ccced93 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node and control-plane. -@@ -832,6 +891,34 @@ spec: +@@ -831,6 +890,34 @@ spec: type: object type: array type: object @@ -284,7 +301,7 @@ index 609887790..12ccced93 100644 type: object mounts: description: Mounts specifies a list of mount points to be setup. -@@ -1096,6 +1183,21 @@ spec: +@@ -1098,6 +1185,21 @@ spec: schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -306,7 +323,7 @@ index 609887790..12ccced93 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, this will -@@ -1302,6 +1404,34 @@ spec: +@@ -1298,6 +1400,34 @@ spec: if that's unset. type: string type: object @@ -341,15 +358,7 @@ index 609887790..12ccced93 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -1491,6 +1621,7 @@ spec: - enum: - - cloud-config - - ignition -+ - bottlerocket - type: string - ignition: - description: Ignition contains Ignition specific configuration. -@@ -1718,6 +1849,21 @@ spec: +@@ -1651,6 +1781,21 @@ spec: schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -371,7 +380,15 @@ index 609887790..12ccced93 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node and control-plane. -@@ -1921,6 +2067,34 @@ spec: +@@ -2481,6 +2626,7 @@ spec: + enum: + - cloud-config + - ignition ++ - bottlerocket + type: string + ignition: + description: Ignition contains Ignition specific configuration. +@@ -2689,6 +2835,34 @@ spec: content inline or by referencing a secret. type: string type: object @@ -407,10 +424,10 @@ index 609887790..12ccced93 100644 description: SkipPhases is a list of phases to skip during command execution. The list of phases can be obtained with the "kubeadm diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -index 0ad80adfb..6a4f04b29 100644 +index 5b30cf21a..adf6c718e 100644 --- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -@@ -116,6 +116,22 @@ spec: +@@ -111,6 +111,22 @@ spec: convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -433,7 +450,7 @@ index 0ad80adfb..6a4f04b29 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, -@@ -330,6 +346,36 @@ spec: +@@ -327,6 +343,36 @@ spec: or to "10.96.0.0/12" if that's unset. type: string type: object @@ -470,7 +487,7 @@ index 0ad80adfb..6a4f04b29 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -525,6 +571,7 @@ spec: +@@ -527,6 +573,7 @@ spec: data enum: - cloud-config @@ -478,7 +495,7 @@ index 0ad80adfb..6a4f04b29 100644 type: string initConfiguration: description: InitConfiguration along with ClusterConfiguration -@@ -705,6 +752,22 @@ spec: +@@ -703,6 +750,22 @@ spec: convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -501,7 +518,7 @@ index 0ad80adfb..6a4f04b29 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node -@@ -888,6 +951,36 @@ spec: +@@ -884,6 +947,36 @@ spec: type: object type: array type: object @@ -538,7 +555,7 @@ index 0ad80adfb..6a4f04b29 100644 type: object mounts: description: Mounts specifies a list of mount points to be -@@ -1119,6 +1212,22 @@ spec: +@@ -1094,6 +1187,22 @@ spec: convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -561,7 +578,7 @@ index 0ad80adfb..6a4f04b29 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, -@@ -1340,6 +1449,36 @@ spec: +@@ -1308,6 +1417,36 @@ spec: or to "10.96.0.0/12" if that's unset. type: string type: object @@ -598,15 +615,7 @@ index 0ad80adfb..6a4f04b29 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -1540,6 +1679,7 @@ spec: - enum: - - cloud-config - - ignition -+ - bottlerocket - type: string - ignition: - description: Ignition contains Ignition specific configuration. -@@ -1785,6 +1925,22 @@ spec: +@@ -1683,6 +1822,22 @@ spec: convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -629,7 +638,15 @@ index 0ad80adfb..6a4f04b29 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node -@@ -2004,6 +2160,36 @@ spec: +@@ -2518,6 +2673,7 @@ spec: + enum: + - cloud-config + - ignition ++ - bottlerocket + type: string + ignition: + description: Ignition contains Ignition specific configuration. +@@ -2744,6 +2900,36 @@ spec: content inline or by referencing a secret. type: string type: object @@ -1365,11 +1382,89 @@ index 99a9cbaa2..ba57b38a8 100644 default: bootstrapJoinData, err = cloudinit.NewJoinControlPlane(controlPlaneJoinInput) } +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/types.go b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +index 3f90b4611..2570daa4f 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/types.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +@@ -55,6 +55,21 @@ type InitConfiguration struct { + type ClusterConfiguration struct { + metav1.TypeMeta `json:",inline"` + ++ // Pause holds the image source for pause container ++ // This is only for bottlerocket ++ // +optional ++ Pause Pause `json:"pause,omitempty"` ++ ++ // BottlerocketBootstrap holds the image source for kubeadm bootstrap container ++ // This is only for bottlerocket ++ // +optional ++ BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` ++ ++ // Proxy holds the https and no proxy information ++ // This is only for bottlerocket ++ // +optional ++ Proxy ProxyConfiguration `json:"proxy,omitempty"` ++ + // Etcd holds configuration for etcd. + // NB: This value defaults to a Local (stacked) etcd + // +optional +@@ -126,6 +141,29 @@ type ClusterConfiguration struct { + ClusterName string `json:"clusterName,omitempty"` + } + ++// Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. ++// This setting is ONLY for bottlerocket nodes, as this needs to be set pre-boot time along with user-data ++type Pause struct { ++ // ImageMeta allows to customize the image used for the Pause component ++ ImageMeta `json:",inline"` ++} ++ ++// BottlerocketBootstrap holds the settings of kubeadm bootstrap container for bottlerocket nodes ++// This setting is ONLY for bottlerocket nodes. ++type BottlerocketBootstrap struct { ++ // ImageMeta allows to customize the image used for the BottlerocketBootstrap component ++ ImageMeta `json:",inline"` ++} ++ ++// ProxyConfiguration holds the settings for proxying bottlerocket services ++type ProxyConfiguration struct { ++ // HTTPS proxy ++ HTTPSProxy string `json:"httpsProxy,omitempty"` ++ ++ // No proxy, list of ips that should not use proxy ++ NoProxy []string `json:"noProxy,omitempty"` ++} ++ + // ControlPlaneComponent holds settings common to control plane component of the cluster. + type ControlPlaneComponent struct { + // ExtraArgs is an extra set of flags to pass to the control plane component. +@@ -327,6 +365,21 @@ type ExternalEtcd struct { + type JoinConfiguration struct { + metav1.TypeMeta `json:",inline"` + ++ // Pause holds the image source for pause container ++ // This is only for bottlerocket ++ // +optional ++ Pause Pause `json:"pause,omitempty"` ++ ++ // BottlerocketBootstrap holds the image source for kubeadm bootstrap container ++ // This is only for bottlerocket ++ // +optional ++ BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` ++ ++ // Proxy holds the https and no proxy information ++ // This is only for bottlerocket ++ // +optional ++ Proxy ProxyConfiguration `json:"proxy,omitempty"` ++ + // NodeRegistration holds fields that relate to registering the new control-plane node to the cluster. + // When used in the context of control plane nodes, NodeRegistration should remain consistent + // across both InitConfiguration and JoinConfiguration diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -index 5b75edf5a..09f797034 100644 +index eb6893bb8..4c5037de1 100644 --- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -@@ -144,6 +144,22 @@ spec: +@@ -178,6 +178,22 @@ spec: schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -1392,7 +1487,7 @@ index 5b75edf5a..09f797034 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, -@@ -350,6 +366,36 @@ spec: +@@ -387,6 +403,36 @@ spec: "10.96.0.0/12" if that's unset. type: string type: object @@ -1429,7 +1524,7 @@ index 5b75edf5a..09f797034 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -541,6 +587,7 @@ spec: +@@ -583,6 +629,7 @@ spec: data enum: - cloud-config @@ -1437,7 +1532,7 @@ index 5b75edf5a..09f797034 100644 type: string initConfiguration: description: InitConfiguration along with ClusterConfiguration -@@ -717,6 +764,22 @@ spec: +@@ -755,6 +802,22 @@ spec: schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -1460,7 +1555,7 @@ index 5b75edf5a..09f797034 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node and -@@ -895,6 +958,36 @@ spec: +@@ -931,6 +994,36 @@ spec: type: object type: array type: object @@ -1497,7 +1592,7 @@ index 5b75edf5a..09f797034 100644 type: object mounts: description: Mounts specifies a list of mount points to be setup. -@@ -1364,6 +1457,22 @@ spec: +@@ -1318,6 +1411,22 @@ spec: schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -1520,7 +1615,7 @@ index 5b75edf5a..09f797034 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, -@@ -1577,6 +1686,36 @@ spec: +@@ -1524,6 +1633,36 @@ spec: "10.96.0.0/12" if that's unset. type: string type: object @@ -1557,15 +1652,7 @@ index 5b75edf5a..09f797034 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -1773,6 +1912,7 @@ spec: - enum: - - cloud-config - - ignition -+ - bottlerocket - type: string - ignition: - description: Ignition contains Ignition specific configuration. -@@ -2010,6 +2150,22 @@ spec: +@@ -1891,6 +2030,22 @@ spec: schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -1588,7 +1675,15 @@ index 5b75edf5a..09f797034 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node and -@@ -2223,6 +2379,36 @@ spec: +@@ -2947,6 +3102,7 @@ spec: + enum: + - cloud-config + - ignition ++ - bottlerocket + type: string + ignition: + description: Ignition contains Ignition specific configuration. +@@ -3165,6 +3321,36 @@ spec: or by referencing a secret. type: string type: object @@ -1764,5 +1859,5 @@ index da5d6a080..dd4f1e72f 100644 description: SkipPhases is a list of phases to skip during command execution. The list of phases can -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0002-Add-unstacked-etcd-support.patch b/projects/kubernetes-sigs/cluster-api/patches/0002-Add-unstacked-etcd-support.patch index b910aeb7bd..1f92447d10 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0002-Add-unstacked-etcd-support.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0002-Add-unstacked-etcd-support.patch @@ -1,4 +1,4 @@ -From 37cad853d2554664b634ee982d3cb3da34f76e9f Mon Sep 17 00:00:00 2001 +From bae12aae7aa733b4fea934cca2d072c084dfcc14 Mon Sep 17 00:00:00 2001 From: Rajashree Mandaogane Date: Mon, 28 Jun 2021 13:44:50 -0700 Subject: [PATCH 02/40] Add unstacked etcd support @@ -68,26 +68,30 @@ commits on the new 1.0.1 branch. This commit adds back the permission. --- api/v1alpha4/cluster_types.go | 14 ++ api/v1beta1/cluster_types.go | 14 ++ - api/v1beta1/condition_consts.go | 16 +++ + api/v1beta1/condition_consts.go | 16 ++ api/v1beta1/machine_types.go | 3 + cmd/clusterctl/client/cluster/mover.go | 3 +- - .../crd/bases/cluster.x-k8s.io_clusters.yaml | 96 +++++++++++++ + .../crd/bases/cluster.x-k8s.io_clusters.yaml | 144 ++++++++++++++++++ config/rbac/role.yaml | 15 ++ controllers/external/util.go | 10 ++ controlplane/kubeadm/config/rbac/role.yaml | 9 ++ .../internal/controllers/controller.go | 51 ++++++- - .../controllers/cluster/cluster_controller.go | 90 +++++++++++- - .../cluster/cluster_controller_phases.go | 108 ++++++++++++++ - .../cluster/cluster_controller_test.go | 136 ++++++++++++++++++ - .../machine/machine_controller_noderef.go | 8 ++ + internal/apis/core/v1alpha3/cluster_types.go | 14 ++ + .../apis/core/v1alpha3/condition_consts.go | 16 ++ + internal/apis/core/v1alpha3/conversion.go | 12 ++ + .../core/v1alpha3/zz_generated.conversion.go | 6 + + .../controllers/cluster/cluster_controller.go | 90 ++++++++++- + .../cluster/cluster_controller_phases.go | 108 +++++++++++++ + .../cluster/cluster_controller_test.go | 136 +++++++++++++++++ + .../machine/machine_controller_noderef.go | 8 + .../machine_controller_noderef_test.go | 43 ++++++ - .../machine/machine_controller_phases.go | 115 +++++++++++++++ + .../machine/machine_controller_phases.go | 115 ++++++++++++++ .../controllers/dockermachine_controller.go | 35 +++-- util/collections/machine_filters.go | 26 ++++ util/secret/certificates.go | 3 + util/secret/consts.go | 2 + util/util.go | 6 + - 21 files changed, 781 insertions(+), 22 deletions(-) + 25 files changed, 877 insertions(+), 22 deletions(-) diff --git a/api/v1alpha4/cluster_types.go b/api/v1alpha4/cluster_types.go index d4ee0658e..207cdcf76 100644 @@ -209,10 +213,10 @@ index ea9c742ab..61270d3a7 100644 } } diff --git a/config/crd/bases/cluster.x-k8s.io_clusters.yaml b/config/crd/bases/cluster.x-k8s.io_clusters.yaml -index f8bd0a426..ab514c177 100644 +index f052a5b8e..a10bee3ce 100644 --- a/config/crd/bases/cluster.x-k8s.io_clusters.yaml +++ b/config/crd/bases/cluster.x-k8s.io_clusters.yaml -@@ -174,6 +174,45 @@ spec: +@@ -169,6 +169,45 @@ spec: type: string type: object x-kubernetes-map-type: atomic @@ -258,7 +262,7 @@ index f8bd0a426..ab514c177 100644 paused: description: Paused can be used to prevent controllers from processing the Cluster and all its associated objects. -@@ -391,6 +430,15 @@ spec: +@@ -261,6 +300,15 @@ spec: description: InfrastructureReady is the state of the infrastructure provider. type: boolean @@ -274,7 +278,7 @@ index f8bd0a426..ab514c177 100644 observedGeneration: description: ObservedGeneration is the latest generation observed by the controller. -@@ -569,6 +617,45 @@ spec: +@@ -432,6 +480,45 @@ spec: type: string type: object x-kubernetes-map-type: atomic @@ -320,7 +324,69 @@ index f8bd0a426..ab514c177 100644 paused: description: Paused can be used to prevent controllers from processing the Cluster and all its associated objects. -@@ -1369,6 +1456,15 @@ spec: +@@ -649,6 +736,15 @@ spec: + description: InfrastructureReady is the state of the infrastructure + provider. + type: boolean ++ managedExternalEtcdInitialized: ++ description: ManagedExternalEtcdInitialized indicates that first etcd ++ member's IP address is set by machine controller, so remaining etcd ++ members can lookup the address to join the cluster ++ type: boolean ++ managedExternalEtcdReady: ++ description: ManagedExternalEtcdReady indicates external etcd cluster ++ is fully provisioned ++ type: boolean + observedGeneration: + description: ObservedGeneration is the latest generation observed + by the controller. +@@ -827,6 +923,45 @@ spec: + type: string + type: object + x-kubernetes-map-type: atomic ++ managedExternalEtcdRef: ++ description: ManagedExternalEtcdRef is an optional reference to an ++ etcd provider resource that holds details for provisioning an external ++ etcd cluster ++ properties: ++ apiVersion: ++ description: API version of the referent. ++ type: string ++ fieldPath: ++ description: 'If referring to a piece of an object instead of ++ an entire object, this string should contain a valid JSON/Go ++ field access statement, such as desiredState.manifest.containers[2]. ++ For example, if the object reference is to a container within ++ a pod, this would take on a value like: "spec.containers{name}" ++ (where "name" refers to the name of the container that triggered ++ the event) or if no container name is specified "spec.containers[2]" ++ (container with index 2 in this pod). This syntax is chosen ++ only to have some well-defined way of referencing a part of ++ an object. TODO: this design is not final and this field is ++ subject to change in the future.' ++ type: string ++ kind: ++ description: 'Kind of the referent. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' ++ type: string ++ name: ++ description: 'Name of the referent. More info: https://kubernetes.io/docs/concepts/overview/working-with-objects/names/#names' ++ type: string ++ namespace: ++ description: 'Namespace of the referent. More info: https://kubernetes.io/docs/concepts/overview/working-with-objects/namespaces/' ++ type: string ++ resourceVersion: ++ description: 'Specific resourceVersion to which this reference ++ is made, if any. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#concurrency-control-and-consistency' ++ type: string ++ uid: ++ description: 'UID of the referent. More info: https://kubernetes.io/docs/concepts/overview/working-with-objects/names/#uids' ++ type: string ++ type: object ++ x-kubernetes-map-type: atomic + paused: + description: Paused can be used to prevent controllers from processing + the Cluster and all its associated objects. +@@ -1627,6 +1762,15 @@ spec: description: InfrastructureReady is the state of the infrastructure provider. type: boolean @@ -494,6 +560,130 @@ index f71bdec07..9bdafa7ec 100644 allMachinePools := &expv1.MachinePoolList{} // Get all machine pools. if feature.Gates.Enabled(feature.MachinePool) { +diff --git a/internal/apis/core/v1alpha3/cluster_types.go b/internal/apis/core/v1alpha3/cluster_types.go +index 2421a2796..88f945742 100644 +--- a/internal/apis/core/v1alpha3/cluster_types.go ++++ b/internal/apis/core/v1alpha3/cluster_types.go +@@ -55,6 +55,11 @@ type ClusterSpec struct { + // +optional + ControlPlaneRef *corev1.ObjectReference `json:"controlPlaneRef,omitempty"` + ++ // ManagedExternalEtcdRef is an optional reference to an etcd provider resource that holds details ++ // for provisioning an external etcd cluster ++ // +optional ++ ManagedExternalEtcdRef *corev1.ObjectReference `json:"managedExternalEtcdRef,omitempty"` ++ + // InfrastructureRef is a reference to a provider-specific resource that holds the details + // for provisioning infrastructure for a cluster in said provider. + // +optional +@@ -146,6 +151,15 @@ type ClusterStatus struct { + // ObservedGeneration is the latest generation observed by the controller. + // +optional + ObservedGeneration int64 `json:"observedGeneration,omitempty"` ++ ++ // ManagedExternalEtcdInitialized indicates that first etcd member's IP address is set by machine controller, ++ // so remaining etcd members can lookup the address to join the cluster ++ // +optional ++ ManagedExternalEtcdInitialized bool `json:"managedExternalEtcdInitialized"` ++ ++ // ManagedExternalEtcdReady indicates external etcd cluster is fully provisioned ++ // +optional ++ ManagedExternalEtcdReady bool `json:"managedExternalEtcdReady"` + } + + // ANCHOR_END: ClusterStatus +diff --git a/internal/apis/core/v1alpha3/condition_consts.go b/internal/apis/core/v1alpha3/condition_consts.go +index 3c0b6195e..c9fd9e27e 100644 +--- a/internal/apis/core/v1alpha3/condition_consts.go ++++ b/internal/apis/core/v1alpha3/condition_consts.go +@@ -184,3 +184,19 @@ const ( + // from making any further remediations. + TooManyUnhealthyReason = "TooManyUnhealthy" + ) ++ ++// Conditions used by the Etcd provider objects ++const ( ++ // ManagedExternalEtcdClusterInitializedCondition is set once the first member of an etcd cluster is provisioned and running ++ ManagedExternalEtcdClusterInitializedCondition ConditionType = "ManagedEtcdInitialized" ++ ++ // ManagedExternalEtcdClusterReadyCondition indicates if the etcd cluster is ready and all members have passed healthchecks. ++ ManagedExternalEtcdClusterReadyCondition ConditionType = "ManagedEtcdReady" ++ ++ // WaitingForEtcdClusterInitializedReason (Severity=Info) documents a cluster waiting for the etcd cluster ++ // to report successful etcd cluster initialization. ++ WaitingForEtcdClusterInitializedReason = "WaitingForEtcdClusterProviderInitialized" ++ ++ // EtcdHealthCheckFailedReason (Severity=Error) documents that healthcheck on an etcd member failed ++ EtcdHealthCheckFailedReason = "EtcdMemberHealthCheckFailed" ++) +diff --git a/internal/apis/core/v1alpha3/conversion.go b/internal/apis/core/v1alpha3/conversion.go +index 9352eb4de..39dfffb4e 100644 +--- a/internal/apis/core/v1alpha3/conversion.go ++++ b/internal/apis/core/v1alpha3/conversion.go +@@ -39,6 +39,14 @@ func (src *Cluster) ConvertTo(dstRaw conversion.Hub) error { + conditions.MarkTrue(dst, clusterv1.ControlPlaneInitializedCondition) + } + ++ if src.Status.ManagedExternalEtcdInitialized { ++ conditions.MarkTrue(dst, clusterv1.ManagedExternalEtcdClusterInitializedCondition) ++ } ++ ++ if src.Status.ManagedExternalEtcdReady { ++ conditions.MarkTrue(dst, clusterv1.ManagedExternalEtcdClusterReadyCondition) ++ } ++ + // Manually restore data. + restored := &clusterv1.Cluster{} + if ok, err := utilconversion.UnmarshalData(src, restored); err != nil || !ok { +@@ -49,6 +57,10 @@ func (src *Cluster) ConvertTo(dstRaw conversion.Hub) error { + dst.Spec.Topology = restored.Spec.Topology + } + ++ if restored.Spec.ManagedExternalEtcdRef != nil { ++ dst.Spec.ManagedExternalEtcdRef = restored.Spec.ManagedExternalEtcdRef ++ } ++ + return nil + } + +diff --git a/internal/apis/core/v1alpha3/zz_generated.conversion.go b/internal/apis/core/v1alpha3/zz_generated.conversion.go +index c7ea14ba3..30a689e8e 100644 +--- a/internal/apis/core/v1alpha3/zz_generated.conversion.go ++++ b/internal/apis/core/v1alpha3/zz_generated.conversion.go +@@ -510,6 +510,7 @@ func autoConvert_v1alpha3_ClusterSpec_To_v1beta1_ClusterSpec(in *ClusterSpec, ou + return err + } + out.ControlPlaneRef = (*v1.ObjectReference)(unsafe.Pointer(in.ControlPlaneRef)) ++ out.ManagedExternalEtcdRef = (*v1.ObjectReference)(unsafe.Pointer(in.ManagedExternalEtcdRef)) + out.InfrastructureRef = (*v1.ObjectReference)(unsafe.Pointer(in.InfrastructureRef)) + return nil + } +@@ -526,6 +527,7 @@ func autoConvert_v1beta1_ClusterSpec_To_v1alpha3_ClusterSpec(in *v1beta1.Cluster + return err + } + out.ControlPlaneRef = (*v1.ObjectReference)(unsafe.Pointer(in.ControlPlaneRef)) ++ out.ManagedExternalEtcdRef = (*v1.ObjectReference)(unsafe.Pointer(in.ManagedExternalEtcdRef)) + out.InfrastructureRef = (*v1.ObjectReference)(unsafe.Pointer(in.InfrastructureRef)) + // WARNING: in.Topology requires manual conversion: does not exist in peer-type + return nil +@@ -541,6 +543,8 @@ func autoConvert_v1alpha3_ClusterStatus_To_v1beta1_ClusterStatus(in *ClusterStat + out.ControlPlaneReady = in.ControlPlaneReady + out.Conditions = *(*v1beta1.Conditions)(unsafe.Pointer(&in.Conditions)) + out.ObservedGeneration = in.ObservedGeneration ++ out.ManagedExternalEtcdInitialized = in.ManagedExternalEtcdInitialized ++ out.ManagedExternalEtcdReady = in.ManagedExternalEtcdReady + return nil + } + +@@ -553,6 +557,8 @@ func autoConvert_v1beta1_ClusterStatus_To_v1alpha3_ClusterStatus(in *v1beta1.Clu + out.ControlPlaneReady = in.ControlPlaneReady + out.Conditions = *(*Conditions)(unsafe.Pointer(&in.Conditions)) + out.ObservedGeneration = in.ObservedGeneration ++ out.ManagedExternalEtcdInitialized = in.ManagedExternalEtcdInitialized ++ out.ManagedExternalEtcdReady = in.ManagedExternalEtcdReady + return nil + } + diff --git a/internal/controllers/cluster/cluster_controller.go b/internal/controllers/cluster/cluster_controller.go index 7654b788a..269007490 100644 --- a/internal/controllers/cluster/cluster_controller.go @@ -1062,7 +1252,7 @@ index 0bcaaa1d0..f3586efa5 100644 + } +} diff --git a/internal/controllers/machine/machine_controller_phases.go b/internal/controllers/machine/machine_controller_phases.go -index 5e34f8904..8eae496e0 100644 +index 8c197b4c1..e22977cc0 100644 --- a/internal/controllers/machine/machine_controller_phases.go +++ b/internal/controllers/machine/machine_controller_phases.go @@ -19,6 +19,7 @@ package machine @@ -1073,7 +1263,7 @@ index 5e34f8904..8eae496e0 100644 "time" "github.com/pkg/errors" -@@ -70,6 +71,13 @@ func (r *Reconciler) reconcilePhase(_ context.Context, m *clusterv1.Machine) { +@@ -68,6 +69,13 @@ func (r *Reconciler) reconcilePhase(_ context.Context, m *clusterv1.Machine) { m.Status.SetTypedPhase(clusterv1.MachinePhaseRunning) } @@ -1087,7 +1277,7 @@ index 5e34f8904..8eae496e0 100644 // Set the phase to "failed" if any of Status.FailureReason or Status.FailureMessage is not-nil. if m.Status.FailureReason != nil || m.Status.FailureMessage != nil { m.Status.SetTypedPhase(clusterv1.MachinePhaseFailed) -@@ -307,6 +315,113 @@ func (r *Reconciler) reconcileInfrastructure(ctx context.Context, s *scope) (ctr +@@ -321,6 +329,113 @@ func (r *Reconciler) reconcileInfrastructure(ctx context.Context, s *scope) (ctr return ctrl.Result{}, errors.Wrapf(err, "failed to retrieve addresses from infrastructure provider for Machine %q in namespace %q", m.Name, m.Namespace) } @@ -1344,5 +1534,5 @@ index d72947ecf..e830011d9 100644 func GetClusterFromMetadata(ctx context.Context, c client.Client, obj metav1.ObjectMeta) (*clusterv1.Cluster, error) { if obj.Labels[clusterv1.ClusterNameLabel] == "" { -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0003-Unstacked-etcd-and-controlplane-upgrade.patch b/projects/kubernetes-sigs/cluster-api/patches/0003-Unstacked-etcd-and-controlplane-upgrade.patch index b3d20e2ba5..b249cbf5d4 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0003-Unstacked-etcd-and-controlplane-upgrade.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0003-Unstacked-etcd-and-controlplane-upgrade.patch @@ -1,4 +1,4 @@ -From 197a571c57027688a81a2b9a4a9f7ab33fb3f0d4 Mon Sep 17 00:00:00 2001 +From b058b9408a0991cc9422bcfedc5612897cb3c51a Mon Sep 17 00:00:00 2001 From: Rajashree Mandaogane Date: Fri, 6 Aug 2021 17:16:39 -0700 Subject: [PATCH 03/40] Unstacked etcd and controlplane upgrade @@ -1186,5 +1186,5 @@ index 47dc7fc6b..e611502ae 100644 func hasAnnotation(o metav1.Object, annotation string) bool { annotations := o.GetAnnotations() -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0004-Patch-config-path-in-kubevip-manifest-for-kubeadm-co.patch b/projects/kubernetes-sigs/cluster-api/patches/0004-Patch-config-path-in-kubevip-manifest-for-kubeadm-co.patch index c4cb94da4b..7aeaf6f5ee 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0004-Patch-config-path-in-kubevip-manifest-for-kubeadm-co.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0004-Patch-config-path-in-kubevip-manifest-for-kubeadm-co.patch @@ -1,4 +1,4 @@ -From 47d39f6072e399f180663f49c2f8e46e95aa2669 Mon Sep 17 00:00:00 2001 +From 5f47bffb6265117f37202b7caa9184cb47fa84b3 Mon Sep 17 00:00:00 2001 From: Guillermo Gaston Date: Thu, 19 Aug 2021 21:52:52 +0000 Subject: [PATCH 04/40] Patch config path in kubevip manifest for kubeadm @@ -27,5 +27,5 @@ index b93e1164b..aecbda8f4 100644 if err != nil { return nil, errors.Wrapf(err, "failed to generate user data for machine joining control plane") -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0005-Make-pause-and-bottlerocket-bootstrap-images-updatab.patch b/projects/kubernetes-sigs/cluster-api/patches/0005-Make-pause-and-bottlerocket-bootstrap-images-updatab.patch index 450d32fdae..7452e63203 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0005-Make-pause-and-bottlerocket-bootstrap-images-updatab.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0005-Make-pause-and-bottlerocket-bootstrap-images-updatab.patch @@ -1,4 +1,4 @@ -From ddb83ecee534a1d7e941ef148e3eaf9c39951b48 Mon Sep 17 00:00:00 2001 +From 9eb0a8e8fa5eea978b8e63a935b7d80f3a9352fe Mon Sep 17 00:00:00 2001 From: Guillermo Gaston Date: Tue, 31 Aug 2021 15:56:28 +0000 Subject: [PATCH 05/40] Make pause and bottlerocket bootstrap images updatable @@ -87,5 +87,5 @@ index bc6dcc07f..275f2cb12 100644 for _, tt := range tests { -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0006-add-support-for-registry-mirror-for-bottlerocket.patch b/projects/kubernetes-sigs/cluster-api/patches/0006-add-support-for-registry-mirror-for-bottlerocket.patch index 7a70cc6a40..42ede18a0b 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0006-add-support-for-registry-mirror-for-bottlerocket.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0006-add-support-for-registry-mirror-for-bottlerocket.patch @@ -1,4 +1,4 @@ -From 5c8b66500b3504835b9a4473f103d40761e9cf76 Mon Sep 17 00:00:00 2001 +From 35980864878f7856bcdce370844acb25057e7bd9 Mon Sep 17 00:00:00 2001 From: Abhinav Pandey Date: Tue, 21 Sep 2021 08:57:56 -0700 Subject: [PATCH 06/40] add support for registry mirror for bottlerocket @@ -10,9 +10,10 @@ Subject: [PATCH 06/40] add support for registry mirror for bottlerocket .../internal/bottlerocket/bootstrap.go | 19 +++++++ .../internal/bottlerocket/bottlerocket.go | 20 +++++-- .../controllers/kubeadmconfig_controller.go | 9 ++++ + .../kubeadm/types/upstreamv1beta1/types.go | 19 +++++++ ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 52 +++++++++++++++++++ ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 26 ++++++++++ - 8 files changed, 241 insertions(+), 4 deletions(-) + 9 files changed, 260 insertions(+), 4 deletions(-) diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go index 11aa737a7..9676d26a8 100644 @@ -59,10 +60,10 @@ index 11aa737a7..9676d26a8 100644 // When used in the context of control plane nodes, NodeRegistration should remain consistent // across both InitConfiguration and JoinConfiguration diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -index 12ccced93..5baf0eb85 100644 +index e2ebd6fb6..ab6e724ca 100644 --- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -@@ -351,6 +351,18 @@ spec: +@@ -349,6 +349,18 @@ spec: type: string type: array type: object @@ -81,7 +82,7 @@ index 12ccced93..5baf0eb85 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -919,6 +931,18 @@ spec: +@@ -918,6 +930,18 @@ spec: type: string type: array type: object @@ -100,7 +101,7 @@ index 12ccced93..5baf0eb85 100644 type: object mounts: description: Mounts specifies a list of mount points to be setup. -@@ -1432,6 +1456,18 @@ spec: +@@ -1428,6 +1452,18 @@ spec: type: string type: array type: object @@ -119,7 +120,7 @@ index 12ccced93..5baf0eb85 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -2095,6 +2131,18 @@ spec: +@@ -2863,6 +2899,18 @@ spec: type: string type: array type: object @@ -139,10 +140,10 @@ index 12ccced93..5baf0eb85 100644 description: SkipPhases is a list of phases to skip during command execution. The list of phases can be obtained with the "kubeadm diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -index 6a4f04b29..a1974c4c9 100644 +index adf6c718e..bdf596e4c 100644 --- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -@@ -376,6 +376,19 @@ spec: +@@ -373,6 +373,19 @@ spec: type: string type: array type: object @@ -162,7 +163,7 @@ index 6a4f04b29..a1974c4c9 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -981,6 +994,19 @@ spec: +@@ -977,6 +990,19 @@ spec: type: string type: array type: object @@ -182,7 +183,7 @@ index 6a4f04b29..a1974c4c9 100644 type: object mounts: description: Mounts specifies a list of mount points to be -@@ -1479,6 +1505,19 @@ spec: +@@ -1447,6 +1473,19 @@ spec: type: string type: array type: object @@ -202,7 +203,7 @@ index 6a4f04b29..a1974c4c9 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -2190,6 +2229,19 @@ spec: +@@ -2930,6 +2969,19 @@ spec: type: string type: array type: object @@ -344,11 +345,55 @@ index ba57b38a8..cbc236823 100644 bootstrapJoinData, err = bottlerocket.NewJoinControlPlane(controlPlaneJoinInput, bottlerocketConfig) if err != nil { scope.Error(err, "Failed to generate cloud init for bottlerocket bootstrap control plane") +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/types.go b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +index 2570daa4f..8fe3ee5ae 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/types.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +@@ -70,6 +70,11 @@ type ClusterConfiguration struct { + // +optional + Proxy ProxyConfiguration `json:"proxy,omitempty"` + ++ // RegistryMirror holds the image registry mirror information ++ // This is only for bottlerocket ++ // +optional ++ RegistryMirror RegistryMirrorConfiguration `json:"registryMirror,omitempty"` ++ + // Etcd holds configuration for etcd. + // NB: This value defaults to a Local (stacked) etcd + // +optional +@@ -164,6 +169,15 @@ type ProxyConfiguration struct { + NoProxy []string `json:"noProxy,omitempty"` + } + ++// RegistryMirrorConfiguration holds the settings for image registry mirror ++type RegistryMirrorConfiguration struct { ++ // Endpoint defines the registry mirror endpoint to use for pulling images ++ Endpoint string `json:"endpoint,omitempty"` ++ ++ // CACert defines the CA cert for the registry mirror ++ CACert string `json:"caCert,omitempty"` ++} ++ + // ControlPlaneComponent holds settings common to control plane component of the cluster. + type ControlPlaneComponent struct { + // ExtraArgs is an extra set of flags to pass to the control plane component. +@@ -380,6 +394,11 @@ type JoinConfiguration struct { + // +optional + Proxy ProxyConfiguration `json:"proxy,omitempty"` + ++ // RegistryMirror holds the image registry mirror information ++ // This is only for bottlerocket ++ // +optional ++ RegistryMirror RegistryMirrorConfiguration `json:"registryMirror,omitempty"` ++ + // NodeRegistration holds fields that relate to registering the new control-plane node to the cluster. + // When used in the context of control plane nodes, NodeRegistration should remain consistent + // across both InitConfiguration and JoinConfiguration diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -index 09f797034..a0ee31f83 100644 +index 4c5037de1..0e19a7e4a 100644 --- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -@@ -396,6 +396,19 @@ spec: +@@ -433,6 +433,19 @@ spec: type: string type: array type: object @@ -368,7 +413,7 @@ index 09f797034..a0ee31f83 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -988,6 +1001,19 @@ spec: +@@ -1024,6 +1037,19 @@ spec: type: string type: array type: object @@ -388,7 +433,7 @@ index 09f797034..a0ee31f83 100644 type: object mounts: description: Mounts specifies a list of mount points to be setup. -@@ -1716,6 +1742,19 @@ spec: +@@ -1663,6 +1689,19 @@ spec: type: string type: array type: object @@ -408,7 +453,7 @@ index 09f797034..a0ee31f83 100644 scheduler: description: Scheduler contains extra settings for the scheduler control plane component -@@ -2409,6 +2448,19 @@ spec: +@@ -3351,6 +3390,19 @@ spec: type: string type: array type: object @@ -473,5 +518,5 @@ index dd4f1e72f..e68ddbdee 100644 description: SkipPhases is a list of phases to skip during command execution. The list of phases can -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0007-Fix-proxy-template-for-bottlerocket-bootstrap.patch b/projects/kubernetes-sigs/cluster-api/patches/0007-Fix-proxy-template-for-bottlerocket-bootstrap.patch index 2310cc83a9..7f990ba7d7 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0007-Fix-proxy-template-for-bottlerocket-bootstrap.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0007-Fix-proxy-template-for-bottlerocket-bootstrap.patch @@ -1,4 +1,4 @@ -From 8db353e2139e4a65f971e8633b18fb15fdc2c06c Mon Sep 17 00:00:00 2001 +From 59c4a195890abb159fa404bdba5547366f1c7f5f Mon Sep 17 00:00:00 2001 From: Rajashree Mandaogane Date: Thu, 30 Sep 2021 14:04:36 -0700 Subject: [PATCH 07/40] Fix proxy template for bottlerocket bootstrap @@ -67,5 +67,5 @@ index 8d118c70c..74aa7e029 100644 bottlerocketInput.RegistryMirrorCACert = base64.StdEncoding.EncodeToString([]byte(config.RegistryMirrorConfiguration.CACert)) } -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0008-Update-core-conversion-spoke-versions.patch b/projects/kubernetes-sigs/cluster-api/patches/0008-Update-core-conversion-spoke-versions.patch index 255c4d4857..67ebbcf53e 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0008-Update-core-conversion-spoke-versions.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0008-Update-core-conversion-spoke-versions.patch @@ -1,4 +1,4 @@ -From 211f3dc3e2412b8c9e0957278b83db753a6f5ebe Mon Sep 17 00:00:00 2001 +From b6716a5f79319e8919304dc8213399fd05f9269b Mon Sep 17 00:00:00 2001 From: Rajashree Mandaogane Date: Sun, 21 Nov 2021 01:16:11 -0800 Subject: [PATCH 08/40] Update core conversion spoke versions @@ -46,5 +46,5 @@ index e89720cc1..cd4de3836 100644 } -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0009-Add-bottlerocket-changes-to-capbk-v1alpha4-api.patch b/projects/kubernetes-sigs/cluster-api/patches/0009-Add-bottlerocket-changes-to-capbk-v1alpha4-api.patch index 7910ac3151..eab3c2a4cf 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0009-Add-bottlerocket-changes-to-capbk-v1alpha4-api.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0009-Add-bottlerocket-changes-to-capbk-v1alpha4-api.patch @@ -1,18 +1,59 @@ -From 2675ee8024694a3a15ecf6c44a575a7e329b6ddf Mon Sep 17 00:00:00 2001 +From c4fbbdaae5d4f51d9241578ed44acef0ac83c6d7 Mon Sep 17 00:00:00 2001 From: Rajashree Mandaogane Date: Sun, 21 Nov 2021 20:59:58 -0800 Subject: [PATCH 09/40] Add bottlerocket changes to capbk v1alpha4 api --- - .../kubeadm/api/v1alpha4/kubeadm_types.go | 72 ++++++++++ + api/v1alpha4/zz_generated.deepcopy.go | 5 + + api/v1beta1/zz_generated.deepcopy.go | 5 + + .../kubeadm/api/v1alpha4/kubeadm_types.go | 72 +++++++ .../api/v1alpha4/kubeadmconfig_types.go | 2 +- - .../api/v1alpha4/zz_generated.deepcopy.go | 75 +++++++++++ - .../api/v1beta1/zz_generated.deepcopy.go | 75 +++++++++++ - .../kubeadm/types/upstreamv1beta2/types.go | 72 ++++++++++ - .../kubeadm/types/upstreamv1beta3/types.go | 72 ++++++++++ - ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 125 ++++++++++++++++++ - 7 files changed, 492 insertions(+), 1 deletion(-) + .../api/v1alpha4/zz_generated.conversion.go | 180 ++++++++++++++++++ + .../api/v1alpha4/zz_generated.deepcopy.go | 75 ++++++++ + .../api/v1beta1/zz_generated.deepcopy.go | 75 ++++++++ + .../upstreamv1beta1/zz_generated.deepcopy.go | 75 ++++++++ + .../kubeadm/types/upstreamv1beta2/types.go | 72 +++++++ + .../zz_generated.conversion.go | 180 ++++++++++++++++++ + .../upstreamv1beta2/zz_generated.deepcopy.go | 75 ++++++++ + .../kubeadm/types/upstreamv1beta3/types.go | 72 +++++++ + .../zz_generated.conversion.go | 180 ++++++++++++++++++ + .../upstreamv1beta3/zz_generated.deepcopy.go | 75 ++++++++ + ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 125 ++++++++++++ + .../test/builder/zz_generated.deepcopy.go | 23 +++ + 16 files changed, 1290 insertions(+), 1 deletion(-) +diff --git a/api/v1alpha4/zz_generated.deepcopy.go b/api/v1alpha4/zz_generated.deepcopy.go +index ac1ae21e3..7aa525c07 100644 +--- a/api/v1alpha4/zz_generated.deepcopy.go ++++ b/api/v1alpha4/zz_generated.deepcopy.go +@@ -247,6 +247,11 @@ func (in *ClusterSpec) DeepCopyInto(out *ClusterSpec) { + *out = new(v1.ObjectReference) + **out = **in + } ++ if in.ManagedExternalEtcdRef != nil { ++ in, out := &in.ManagedExternalEtcdRef, &out.ManagedExternalEtcdRef ++ *out = new(v1.ObjectReference) ++ **out = **in ++ } + if in.InfrastructureRef != nil { + in, out := &in.InfrastructureRef, &out.InfrastructureRef + *out = new(v1.ObjectReference) +diff --git a/api/v1beta1/zz_generated.deepcopy.go b/api/v1beta1/zz_generated.deepcopy.go +index 7eb964845..5629c4a37 100644 +--- a/api/v1beta1/zz_generated.deepcopy.go ++++ b/api/v1beta1/zz_generated.deepcopy.go +@@ -378,6 +378,11 @@ func (in *ClusterSpec) DeepCopyInto(out *ClusterSpec) { + *out = new(v1.ObjectReference) + **out = **in + } ++ if in.ManagedExternalEtcdRef != nil { ++ in, out := &in.ManagedExternalEtcdRef, &out.ManagedExternalEtcdRef ++ *out = new(v1.ObjectReference) ++ **out = **in ++ } + if in.InfrastructureRef != nil { + in, out := &in.InfrastructureRef, &out.InfrastructureRef + *out = new(v1.ObjectReference) diff --git a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go index 6e91e00ae..29df78f5c 100644 --- a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go @@ -123,6 +164,240 @@ index ccaea9dbc..2682067e8 100644 type Format string const ( +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +index bcc2c3a8c..0e60d4e59 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +@@ -90,6 +90,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrap)(nil), (*v1beta1.BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(a.(*BottlerocketBootstrap), b.(*v1beta1.BottlerocketBootstrap), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketBootstrap)(nil), (*BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(a.(*v1beta1.BottlerocketBootstrap), b.(*BottlerocketBootstrap), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*ClusterConfiguration)(nil), (*v1beta1.ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(a.(*ClusterConfiguration), b.(*v1beta1.ClusterConfiguration), scope) + }); err != nil { +@@ -360,6 +370,36 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*Pause)(nil), (*v1beta1.Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_Pause_To_v1beta1_Pause(a.(*Pause), b.(*v1beta1.Pause), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.Pause)(nil), (*Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_Pause_To_v1alpha4_Pause(a.(*v1beta1.Pause), b.(*Pause), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*ProxyConfiguration)(nil), (*v1beta1.ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(a.(*ProxyConfiguration), b.(*v1beta1.ProxyConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.ProxyConfiguration)(nil), (*ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(a.(*v1beta1.ProxyConfiguration), b.(*ProxyConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*RegistryMirrorConfiguration)(nil), (*v1beta1.RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(a.(*RegistryMirrorConfiguration), b.(*v1beta1.RegistryMirrorConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.RegistryMirrorConfiguration)(nil), (*RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(a.(*v1beta1.RegistryMirrorConfiguration), b.(*RegistryMirrorConfiguration), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*SecretFileSource)(nil), (*v1beta1.SecretFileSource)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1alpha4_SecretFileSource_To_v1beta1_SecretFileSource(a.(*SecretFileSource), b.(*v1beta1.SecretFileSource), scope) + }); err != nil { +@@ -541,7 +581,43 @@ func Convert_v1beta1_BootstrapTokenString_To_v1alpha4_BootstrapTokenString(in *v + return autoConvert_v1beta1_BootstrapTokenString_To_v1alpha4_BootstrapTokenString(in, out, s) + } + ++func autoConvert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { ++ if err := Convert_v1alpha4_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap is an autogenerated conversion function. ++func Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { ++ return autoConvert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { ++ if err := Convert_v1beta1_ImageMeta_To_v1alpha4_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(in, out, s) ++} ++ + func autoConvert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *ClusterConfiguration, out *v1beta1.ClusterConfiguration, s conversion.Scope) error { ++ if err := Convert_v1alpha4_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_v1alpha4_Etcd_To_v1beta1_Etcd(&in.Etcd, &out.Etcd, s); err != nil { + return err + } +@@ -575,6 +651,18 @@ func Convert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *C + } + + func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(in *v1beta1.ClusterConfiguration, out *ClusterConfiguration, s conversion.Scope) error { ++ if err := Convert_v1beta1_Pause_To_v1alpha4_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_v1beta1_Etcd_To_v1alpha4_Etcd(&in.Etcd, &out.Etcd, s); err != nil { + return err + } +@@ -951,6 +1039,18 @@ func autoConvert_v1beta1_InitConfiguration_To_v1alpha4_InitConfiguration(in *v1b + } + + func autoConvert_v1alpha4_JoinConfiguration_To_v1beta1_JoinConfiguration(in *JoinConfiguration, out *v1beta1.JoinConfiguration, s conversion.Scope) error { ++ if err := Convert_v1alpha4_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_v1alpha4_NodeRegistrationOptions_To_v1beta1_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { + return err + } +@@ -968,6 +1068,18 @@ func Convert_v1alpha4_JoinConfiguration_To_v1beta1_JoinConfiguration(in *JoinCon + } + + func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1beta1.JoinConfiguration, out *JoinConfiguration, s conversion.Scope) error { ++ if err := Convert_v1beta1_Pause_To_v1alpha4_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_v1beta1_NodeRegistrationOptions_To_v1alpha4_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { + return err + } +@@ -1481,6 +1593,74 @@ func Convert_v1beta1_Partition_To_v1alpha4_Partition(in *v1beta1.Partition, out + return autoConvert_v1beta1_Partition_To_v1alpha4_Partition(in, out, s) + } + ++func autoConvert_v1alpha4_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { ++ if err := Convert_v1alpha4_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1alpha4_Pause_To_v1beta1_Pause is an autogenerated conversion function. ++func Convert_v1alpha4_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { ++ return autoConvert_v1alpha4_Pause_To_v1beta1_Pause(in, out, s) ++} ++ ++func autoConvert_v1beta1_Pause_To_v1alpha4_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { ++ if err := Convert_v1beta1_ImageMeta_To_v1alpha4_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1beta1_Pause_To_v1alpha4_Pause is an autogenerated conversion function. ++func Convert_v1beta1_Pause_To_v1alpha4_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { ++ return autoConvert_v1beta1_Pause_To_v1alpha4_Pause(in, out, s) ++} ++ ++func autoConvert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { ++ out.HTTPSProxy = in.HTTPSProxy ++ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) ++ return nil ++} ++ ++// Convert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration is an autogenerated conversion function. ++func Convert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { ++ return autoConvert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in, out, s) ++} ++ ++func autoConvert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { ++ out.HTTPSProxy = in.HTTPSProxy ++ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) ++ return nil ++} ++ ++// Convert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration is an autogenerated conversion function. ++func Convert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { ++ return autoConvert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(in, out, s) ++} ++ ++func autoConvert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { ++ out.Endpoint = in.Endpoint ++ out.CACert = in.CACert ++ return nil ++} ++ ++// Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration is an autogenerated conversion function. ++func Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { ++ return autoConvert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in, out, s) ++} ++ ++func autoConvert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { ++ out.Endpoint = in.Endpoint ++ out.CACert = in.CACert ++ return nil ++} ++ ++// Convert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration is an autogenerated conversion function. ++func Convert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { ++ return autoConvert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(in, out, s) ++} ++ + func autoConvert_v1alpha4_SecretFileSource_To_v1beta1_SecretFileSource(in *SecretFileSource, out *v1beta1.SecretFileSource, s conversion.Scope) error { + out.Name = in.Name + out.Key = in.Key diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go index 085cafb92..460e2c11c 100644 --- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go @@ -331,6 +606,107 @@ index 425b90eda..90c8c89be 100644 // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *SecretFileSource) DeepCopyInto(out *SecretFileSource) { *out = *in +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +index aeaaa3aff..258534eb0 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +@@ -141,10 +141,30 @@ func (in *BootstrapTokenString) DeepCopy() *BootstrapTokenString { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootstrap. ++func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketBootstrap) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = *in + out.TypeMeta = in.TypeMeta ++ out.Pause = in.Pause ++ out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ in.Proxy.DeepCopyInto(&out.Proxy) ++ out.RegistryMirror = in.RegistryMirror + in.Etcd.DeepCopyInto(&out.Etcd) + out.Networking = in.Networking + in.APIServer.DeepCopyInto(&out.APIServer) +@@ -409,6 +429,10 @@ func (in *InitConfiguration) DeepCopyObject() runtime.Object { + func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = *in + out.TypeMeta = in.TypeMeta ++ out.Pause = in.Pause ++ out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ in.Proxy.DeepCopyInto(&out.Proxy) ++ out.RegistryMirror = in.RegistryMirror + in.NodeRegistration.DeepCopyInto(&out.NodeRegistration) + in.Discovery.DeepCopyInto(&out.Discovery) + if in.ControlPlane != nil { +@@ -528,3 +552,54 @@ func (in *NodeRegistrationOptions) DeepCopy() *NodeRegistrationOptions { + in.DeepCopyInto(out) + return out + } ++ ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *Pause) DeepCopyInto(out *Pause) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Pause. ++func (in *Pause) DeepCopy() *Pause { ++ if in == nil { ++ return nil ++ } ++ out := new(Pause) ++ in.DeepCopyInto(out) ++ return out ++} ++ ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *ProxyConfiguration) DeepCopyInto(out *ProxyConfiguration) { ++ *out = *in ++ if in.NoProxy != nil { ++ in, out := &in.NoProxy, &out.NoProxy ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ProxyConfiguration. ++func (in *ProxyConfiguration) DeepCopy() *ProxyConfiguration { ++ if in == nil { ++ return nil ++ } ++ out := new(ProxyConfiguration) ++ in.DeepCopyInto(out) ++ return out ++} ++ ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *RegistryMirrorConfiguration) DeepCopyInto(out *RegistryMirrorConfiguration) { ++ *out = *in ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new RegistryMirrorConfiguration. ++func (in *RegistryMirrorConfiguration) DeepCopy() *RegistryMirrorConfiguration { ++ if in == nil { ++ return nil ++ } ++ out := new(RegistryMirrorConfiguration) ++ in.DeepCopyInto(out) ++ return out ++} diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/types.go b/bootstrap/kubeadm/types/upstreamv1beta2/types.go index 413f6fe9b..ff9a01d04 100644 --- a/bootstrap/kubeadm/types/upstreamv1beta2/types.go @@ -428,6 +804,338 @@ index 413f6fe9b..ff9a01d04 100644 // NodeRegistration holds fields that relate to registering the new control-plane node to the cluster. // When used in the context of control plane nodes, NodeRegistration should remain consistent // across both InitConfiguration and JoinConfiguration +diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go +index 9a40da3b2..ae1158152 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go +@@ -88,6 +88,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrap)(nil), (*v1beta1.BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(a.(*BottlerocketBootstrap), b.(*v1beta1.BottlerocketBootstrap), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketBootstrap)(nil), (*BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(a.(*v1beta1.BottlerocketBootstrap), b.(*BottlerocketBootstrap), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*v1beta1.ClusterConfiguration)(nil), (*ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_ClusterConfiguration_To_upstreamv1beta2_ClusterConfiguration(a.(*v1beta1.ClusterConfiguration), b.(*ClusterConfiguration), scope) + }); err != nil { +@@ -213,6 +223,36 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*Pause)(nil), (*v1beta1.Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta2_Pause_To_v1beta1_Pause(a.(*Pause), b.(*v1beta1.Pause), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.Pause)(nil), (*Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_Pause_To_upstreamv1beta2_Pause(a.(*v1beta1.Pause), b.(*Pause), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*ProxyConfiguration)(nil), (*v1beta1.ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(a.(*ProxyConfiguration), b.(*v1beta1.ProxyConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.ProxyConfiguration)(nil), (*ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(a.(*v1beta1.ProxyConfiguration), b.(*ProxyConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*RegistryMirrorConfiguration)(nil), (*v1beta1.RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(a.(*RegistryMirrorConfiguration), b.(*v1beta1.RegistryMirrorConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.RegistryMirrorConfiguration)(nil), (*RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(a.(*v1beta1.RegistryMirrorConfiguration), b.(*RegistryMirrorConfiguration), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddConversionFunc((*ClusterConfiguration)(nil), (*v1beta1.ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_upstreamv1beta2_ClusterConfiguration_To_v1beta1_ClusterConfiguration(a.(*ClusterConfiguration), b.(*v1beta1.ClusterConfiguration), scope) + }); err != nil { +@@ -379,7 +419,43 @@ func Convert_v1beta1_BootstrapTokenString_To_upstreamv1beta2_BootstrapTokenStrin + return autoConvert_v1beta1_BootstrapTokenString_To_upstreamv1beta2_BootstrapTokenString(in, out, s) + } + ++func autoConvert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta2_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap is an autogenerated conversion function. ++func Convert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { ++ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta2_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(in, out, s) ++} ++ + func autoConvert_upstreamv1beta2_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *ClusterConfiguration, out *v1beta1.ClusterConfiguration, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta2_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_upstreamv1beta2_Etcd_To_v1beta1_Etcd(&in.Etcd, &out.Etcd, s); err != nil { + return err + } +@@ -409,6 +485,18 @@ func autoConvert_upstreamv1beta2_ClusterConfiguration_To_v1beta1_ClusterConfigur + } + + func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta2_ClusterConfiguration(in *v1beta1.ClusterConfiguration, out *ClusterConfiguration, s conversion.Scope) error { ++ if err := Convert_v1beta1_Pause_To_upstreamv1beta2_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_v1beta1_Etcd_To_upstreamv1beta2_Etcd(&in.Etcd, &out.Etcd, s); err != nil { + return err + } +@@ -673,6 +761,18 @@ func autoConvert_v1beta1_InitConfiguration_To_upstreamv1beta2_InitConfiguration( + } + + func autoConvert_upstreamv1beta2_JoinConfiguration_To_v1beta1_JoinConfiguration(in *JoinConfiguration, out *v1beta1.JoinConfiguration, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta2_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_upstreamv1beta2_NodeRegistrationOptions_To_v1beta1_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { + return err + } +@@ -698,6 +798,18 @@ func Convert_upstreamv1beta2_JoinConfiguration_To_v1beta1_JoinConfiguration(in * + } + + func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta2_JoinConfiguration(in *v1beta1.JoinConfiguration, out *JoinConfiguration, s conversion.Scope) error { ++ if err := Convert_v1beta1_Pause_To_upstreamv1beta2_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_v1beta1_NodeRegistrationOptions_To_upstreamv1beta2_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { + return err + } +@@ -818,3 +930,71 @@ func autoConvert_v1beta1_NodeRegistrationOptions_To_upstreamv1beta2_NodeRegistra + // WARNING: in.ImagePullPolicy requires manual conversion: does not exist in peer-type + return nil + } ++ ++func autoConvert_upstreamv1beta2_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta2_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_upstreamv1beta2_Pause_To_v1beta1_Pause is an autogenerated conversion function. ++func Convert_upstreamv1beta2_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta2_Pause_To_v1beta1_Pause(in, out, s) ++} ++ ++func autoConvert_v1beta1_Pause_To_upstreamv1beta2_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { ++ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta2_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1beta1_Pause_To_upstreamv1beta2_Pause is an autogenerated conversion function. ++func Convert_v1beta1_Pause_To_upstreamv1beta2_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { ++ return autoConvert_v1beta1_Pause_To_upstreamv1beta2_Pause(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { ++ out.HTTPSProxy = in.HTTPSProxy ++ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) ++ return nil ++} ++ ++// Convert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration is an autogenerated conversion function. ++func Convert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in, out, s) ++} ++ ++func autoConvert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { ++ out.HTTPSProxy = in.HTTPSProxy ++ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) ++ return nil ++} ++ ++// Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration is an autogenerated conversion function. ++func Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { ++ return autoConvert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { ++ out.Endpoint = in.Endpoint ++ out.CACert = in.CACert ++ return nil ++} ++ ++// Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration is an autogenerated conversion function. ++func Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in, out, s) ++} ++ ++func autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { ++ out.Endpoint = in.Endpoint ++ out.CACert = in.CACert ++ return nil ++} ++ ++// Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration is an autogenerated conversion function. ++func Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { ++ return autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(in, out, s) ++} +diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.deepcopy.go +index c4cecbaad..1caece2f9 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.deepcopy.go +@@ -141,10 +141,30 @@ func (in *BootstrapTokenString) DeepCopy() *BootstrapTokenString { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootstrap. ++func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketBootstrap) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = *in + out.TypeMeta = in.TypeMeta ++ out.Pause = in.Pause ++ out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ in.Proxy.DeepCopyInto(&out.Proxy) ++ out.RegistryMirror = in.RegistryMirror + in.Etcd.DeepCopyInto(&out.Etcd) + out.Networking = in.Networking + in.APIServer.DeepCopyInto(&out.APIServer) +@@ -409,6 +429,10 @@ func (in *InitConfiguration) DeepCopyObject() runtime.Object { + func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = *in + out.TypeMeta = in.TypeMeta ++ out.Pause = in.Pause ++ out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ in.Proxy.DeepCopyInto(&out.Proxy) ++ out.RegistryMirror = in.RegistryMirror + in.NodeRegistration.DeepCopyInto(&out.NodeRegistration) + in.Discovery.DeepCopyInto(&out.Discovery) + if in.ControlPlane != nil { +@@ -533,3 +557,54 @@ func (in *NodeRegistrationOptions) DeepCopy() *NodeRegistrationOptions { + in.DeepCopyInto(out) + return out + } ++ ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *Pause) DeepCopyInto(out *Pause) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Pause. ++func (in *Pause) DeepCopy() *Pause { ++ if in == nil { ++ return nil ++ } ++ out := new(Pause) ++ in.DeepCopyInto(out) ++ return out ++} ++ ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *ProxyConfiguration) DeepCopyInto(out *ProxyConfiguration) { ++ *out = *in ++ if in.NoProxy != nil { ++ in, out := &in.NoProxy, &out.NoProxy ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ProxyConfiguration. ++func (in *ProxyConfiguration) DeepCopy() *ProxyConfiguration { ++ if in == nil { ++ return nil ++ } ++ out := new(ProxyConfiguration) ++ in.DeepCopyInto(out) ++ return out ++} ++ ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *RegistryMirrorConfiguration) DeepCopyInto(out *RegistryMirrorConfiguration) { ++ *out = *in ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new RegistryMirrorConfiguration. ++func (in *RegistryMirrorConfiguration) DeepCopy() *RegistryMirrorConfiguration { ++ if in == nil { ++ return nil ++ } ++ out := new(RegistryMirrorConfiguration) ++ in.DeepCopyInto(out) ++ return out ++} diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/types.go b/bootstrap/kubeadm/types/upstreamv1beta3/types.go index abc993a88..42bda5ca0 100644 --- a/bootstrap/kubeadm/types/upstreamv1beta3/types.go @@ -525,6 +1233,338 @@ index abc993a88..42bda5ca0 100644 // NodeRegistration holds fields that relate to registering the new control-plane node to the cluster // +optional NodeRegistration NodeRegistrationOptions `json:"nodeRegistration,omitempty"` +diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go +index d849616cb..9b0c13356 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go +@@ -88,6 +88,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrap)(nil), (*v1beta1.BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(a.(*BottlerocketBootstrap), b.(*v1beta1.BottlerocketBootstrap), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketBootstrap)(nil), (*BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(a.(*v1beta1.BottlerocketBootstrap), b.(*BottlerocketBootstrap), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*ClusterConfiguration)(nil), (*v1beta1.ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_upstreamv1beta3_ClusterConfiguration_To_v1beta1_ClusterConfiguration(a.(*ClusterConfiguration), b.(*v1beta1.ClusterConfiguration), scope) + }); err != nil { +@@ -228,6 +238,36 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*Pause)(nil), (*v1beta1.Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta3_Pause_To_v1beta1_Pause(a.(*Pause), b.(*v1beta1.Pause), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.Pause)(nil), (*Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_Pause_To_upstreamv1beta3_Pause(a.(*v1beta1.Pause), b.(*Pause), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*ProxyConfiguration)(nil), (*v1beta1.ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(a.(*ProxyConfiguration), b.(*v1beta1.ProxyConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.ProxyConfiguration)(nil), (*ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(a.(*v1beta1.ProxyConfiguration), b.(*ProxyConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*RegistryMirrorConfiguration)(nil), (*v1beta1.RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(a.(*RegistryMirrorConfiguration), b.(*v1beta1.RegistryMirrorConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.RegistryMirrorConfiguration)(nil), (*RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(a.(*v1beta1.RegistryMirrorConfiguration), b.(*RegistryMirrorConfiguration), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddConversionFunc((*InitConfiguration)(nil), (*v1beta1.InitConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_upstreamv1beta3_InitConfiguration_To_v1beta1_InitConfiguration(a.(*InitConfiguration), b.(*v1beta1.InitConfiguration), scope) + }); err != nil { +@@ -379,7 +419,43 @@ func Convert_v1beta1_BootstrapTokenString_To_upstreamv1beta3_BootstrapTokenStrin + return autoConvert_v1beta1_BootstrapTokenString_To_upstreamv1beta3_BootstrapTokenString(in, out, s) + } + ++func autoConvert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta3_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap is an autogenerated conversion function. ++func Convert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { ++ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta3_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(in, out, s) ++} ++ + func autoConvert_upstreamv1beta3_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *ClusterConfiguration, out *v1beta1.ClusterConfiguration, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta3_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_upstreamv1beta3_Etcd_To_v1beta1_Etcd(&in.Etcd, &out.Etcd, s); err != nil { + return err + } +@@ -413,6 +489,18 @@ func Convert_upstreamv1beta3_ClusterConfiguration_To_v1beta1_ClusterConfiguratio + } + + func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta3_ClusterConfiguration(in *v1beta1.ClusterConfiguration, out *ClusterConfiguration, s conversion.Scope) error { ++ if err := Convert_v1beta1_Pause_To_upstreamv1beta3_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_v1beta1_Etcd_To_upstreamv1beta3_Etcd(&in.Etcd, &out.Etcd, s); err != nil { + return err + } +@@ -668,6 +756,18 @@ func Convert_v1beta1_InitConfiguration_To_upstreamv1beta3_InitConfiguration(in * + } + + func autoConvert_upstreamv1beta3_JoinConfiguration_To_v1beta1_JoinConfiguration(in *JoinConfiguration, out *v1beta1.JoinConfiguration, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta3_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_upstreamv1beta3_NodeRegistrationOptions_To_v1beta1_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { + return err + } +@@ -690,6 +790,18 @@ func autoConvert_upstreamv1beta3_JoinConfiguration_To_v1beta1_JoinConfiguration( + } + + func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta3_JoinConfiguration(in *v1beta1.JoinConfiguration, out *JoinConfiguration, s conversion.Scope) error { ++ if err := Convert_v1beta1_Pause_To_upstreamv1beta3_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_v1beta1_NodeRegistrationOptions_To_upstreamv1beta3_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { + return err + } +@@ -836,3 +948,71 @@ func autoConvert_v1beta1_Patches_To_upstreamv1beta3_Patches(in *v1beta1.Patches, + func Convert_v1beta1_Patches_To_upstreamv1beta3_Patches(in *v1beta1.Patches, out *Patches, s conversion.Scope) error { + return autoConvert_v1beta1_Patches_To_upstreamv1beta3_Patches(in, out, s) + } ++ ++func autoConvert_upstreamv1beta3_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta3_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_upstreamv1beta3_Pause_To_v1beta1_Pause is an autogenerated conversion function. ++func Convert_upstreamv1beta3_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta3_Pause_To_v1beta1_Pause(in, out, s) ++} ++ ++func autoConvert_v1beta1_Pause_To_upstreamv1beta3_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { ++ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta3_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1beta1_Pause_To_upstreamv1beta3_Pause is an autogenerated conversion function. ++func Convert_v1beta1_Pause_To_upstreamv1beta3_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { ++ return autoConvert_v1beta1_Pause_To_upstreamv1beta3_Pause(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { ++ out.HTTPSProxy = in.HTTPSProxy ++ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) ++ return nil ++} ++ ++// Convert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration is an autogenerated conversion function. ++func Convert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in, out, s) ++} ++ ++func autoConvert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { ++ out.HTTPSProxy = in.HTTPSProxy ++ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) ++ return nil ++} ++ ++// Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration is an autogenerated conversion function. ++func Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { ++ return autoConvert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { ++ out.Endpoint = in.Endpoint ++ out.CACert = in.CACert ++ return nil ++} ++ ++// Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration is an autogenerated conversion function. ++func Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in, out, s) ++} ++ ++func autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { ++ out.Endpoint = in.Endpoint ++ out.CACert = in.CACert ++ return nil ++} ++ ++// Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration is an autogenerated conversion function. ++func Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { ++ return autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(in, out, s) ++} +diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.deepcopy.go +index 77bc8ac51..b7b976a49 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.deepcopy.go +@@ -141,10 +141,30 @@ func (in *BootstrapTokenString) DeepCopy() *BootstrapTokenString { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootstrap. ++func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketBootstrap) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = *in + out.TypeMeta = in.TypeMeta ++ out.Pause = in.Pause ++ out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ in.Proxy.DeepCopyInto(&out.Proxy) ++ out.RegistryMirror = in.RegistryMirror + in.Etcd.DeepCopyInto(&out.Etcd) + out.Networking = in.Networking + in.APIServer.DeepCopyInto(&out.APIServer) +@@ -388,6 +408,10 @@ func (in *InitConfiguration) DeepCopyObject() runtime.Object { + func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = *in + out.TypeMeta = in.TypeMeta ++ out.Pause = in.Pause ++ out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ in.Proxy.DeepCopyInto(&out.Proxy) ++ out.RegistryMirror = in.RegistryMirror + in.NodeRegistration.DeepCopyInto(&out.NodeRegistration) + in.Discovery.DeepCopyInto(&out.Discovery) + if in.ControlPlane != nil { +@@ -537,3 +561,54 @@ func (in *Patches) DeepCopy() *Patches { + in.DeepCopyInto(out) + return out + } ++ ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *Pause) DeepCopyInto(out *Pause) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Pause. ++func (in *Pause) DeepCopy() *Pause { ++ if in == nil { ++ return nil ++ } ++ out := new(Pause) ++ in.DeepCopyInto(out) ++ return out ++} ++ ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *ProxyConfiguration) DeepCopyInto(out *ProxyConfiguration) { ++ *out = *in ++ if in.NoProxy != nil { ++ in, out := &in.NoProxy, &out.NoProxy ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ProxyConfiguration. ++func (in *ProxyConfiguration) DeepCopy() *ProxyConfiguration { ++ if in == nil { ++ return nil ++ } ++ out := new(ProxyConfiguration) ++ in.DeepCopyInto(out) ++ return out ++} ++ ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *RegistryMirrorConfiguration) DeepCopyInto(out *RegistryMirrorConfiguration) { ++ *out = *in ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new RegistryMirrorConfiguration. ++func (in *RegistryMirrorConfiguration) DeepCopy() *RegistryMirrorConfiguration { ++ if in == nil { ++ return nil ++ } ++ out := new(RegistryMirrorConfiguration) ++ in.DeepCopyInto(out) ++ return out ++} diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml index e68ddbdee..d4d5e0073 100644 --- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml @@ -689,6 +1729,47 @@ index e68ddbdee..d4d5e0073 100644 type: object mounts: description: Mounts specifies a list of mount points to +diff --git a/internal/test/builder/zz_generated.deepcopy.go b/internal/test/builder/zz_generated.deepcopy.go +index 4ca1c64ca..64e72d45b 100644 +--- a/internal/test/builder/zz_generated.deepcopy.go ++++ b/internal/test/builder/zz_generated.deepcopy.go +@@ -95,6 +95,10 @@ func (in *ClusterBuilder) DeepCopyInto(out *ClusterBuilder) { + in, out := &in.controlPlane, &out.controlPlane + *out = (*in).DeepCopy() + } ++ if in.managedEtcd != nil { ++ in, out := &in.managedEtcd, &out.managedEtcd ++ *out = (*in).DeepCopy() ++ } + if in.network != nil { + in, out := &in.network, &out.network + *out = new(v1beta1.ClusterNetwork) +@@ -274,6 +278,25 @@ func (in *ControlPlaneTemplateBuilder) DeepCopy() *ControlPlaneTemplateBuilder { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *EtcdPlaneBuilder) DeepCopyInto(out *EtcdPlaneBuilder) { ++ *out = *in ++ if in.obj != nil { ++ in, out := &in.obj, &out.obj ++ *out = (*in).DeepCopy() ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new EtcdPlaneBuilder. ++func (in *EtcdPlaneBuilder) DeepCopy() *EtcdPlaneBuilder { ++ if in == nil { ++ return nil ++ } ++ out := new(EtcdPlaneBuilder) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *InfrastructureClusterBuilder) DeepCopyInto(out *InfrastructureClusterBuilder) { + *out = *in -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0011-Add-status.version-to-list-of-fields-to-ignore-for-u.patch b/projects/kubernetes-sigs/cluster-api/patches/0010-Add-status.version-to-list-of-fields-to-ignore-for-u.patch similarity index 88% rename from projects/kubernetes-sigs/cluster-api/patches/0011-Add-status.version-to-list-of-fields-to-ignore-for-u.patch rename to projects/kubernetes-sigs/cluster-api/patches/0010-Add-status.version-to-list-of-fields-to-ignore-for-u.patch index 7cd72a90b9..20fe268f51 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0011-Add-status.version-to-list-of-fields-to-ignore-for-u.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0010-Add-status.version-to-list-of-fields-to-ignore-for-u.patch @@ -1,7 +1,7 @@ -From ef47ec11378a9e0ecc2ac7088cabcd501349f270 Mon Sep 17 00:00:00 2001 +From 2e6facdcabaa3a7b037fe911dac4e7d081f5e880 Mon Sep 17 00:00:00 2001 From: Vivek Koppuru Date: Wed, 12 Jan 2022 19:04:15 -0800 -Subject: [PATCH 11/40] Add status.version to list of fields to ignore for +Subject: [PATCH 10/40] Add status.version to list of fields to ignore for update --- @@ -29,5 +29,5 @@ index 230b0bebb..477aef2e2 100644 oldK, ok := oldObj.(*controlplanev1.KubeadmControlPlane) -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0010-Update-capbk-converions-spoke-version.patch b/projects/kubernetes-sigs/cluster-api/patches/0010-Update-capbk-converions-spoke-version.patch deleted file mode 100644 index 8982b5fe95..0000000000 --- a/projects/kubernetes-sigs/cluster-api/patches/0010-Update-capbk-converions-spoke-version.patch +++ /dev/null @@ -1,710 +0,0 @@ -From e01e1d2678dcfdc5f2ec74599a55769958408c68 Mon Sep 17 00:00:00 2001 -From: Rajashree Mandaogane -Date: Sun, 21 Nov 2021 21:00:31 -0800 -Subject: [PATCH 10/40] Update capbk converions spoke version - ---- - .../api/v1alpha4/zz_generated.conversion.go | 180 ++++++++++++++++++ - .../zz_generated.conversion.go | 180 ++++++++++++++++++ - .../zz_generated.conversion.go | 180 ++++++++++++++++++ - 3 files changed, 540 insertions(+) - -diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -index bcc2c3a8c..0e60d4e59 100644 ---- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -@@ -90,6 +90,16 @@ func RegisterConversions(s *runtime.Scheme) error { - }); err != nil { - return err - } -+ if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrap)(nil), (*v1beta1.BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(a.(*BottlerocketBootstrap), b.(*v1beta1.BottlerocketBootstrap), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketBootstrap)(nil), (*BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(a.(*v1beta1.BottlerocketBootstrap), b.(*BottlerocketBootstrap), scope) -+ }); err != nil { -+ return err -+ } - if err := s.AddGeneratedConversionFunc((*ClusterConfiguration)(nil), (*v1beta1.ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(a.(*ClusterConfiguration), b.(*v1beta1.ClusterConfiguration), scope) - }); err != nil { -@@ -360,6 +370,36 @@ func RegisterConversions(s *runtime.Scheme) error { - }); err != nil { - return err - } -+ if err := s.AddGeneratedConversionFunc((*Pause)(nil), (*v1beta1.Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1alpha4_Pause_To_v1beta1_Pause(a.(*Pause), b.(*v1beta1.Pause), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.Pause)(nil), (*Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_Pause_To_v1alpha4_Pause(a.(*v1beta1.Pause), b.(*Pause), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*ProxyConfiguration)(nil), (*v1beta1.ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(a.(*ProxyConfiguration), b.(*v1beta1.ProxyConfiguration), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.ProxyConfiguration)(nil), (*ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(a.(*v1beta1.ProxyConfiguration), b.(*ProxyConfiguration), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*RegistryMirrorConfiguration)(nil), (*v1beta1.RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(a.(*RegistryMirrorConfiguration), b.(*v1beta1.RegistryMirrorConfiguration), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.RegistryMirrorConfiguration)(nil), (*RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(a.(*v1beta1.RegistryMirrorConfiguration), b.(*RegistryMirrorConfiguration), scope) -+ }); err != nil { -+ return err -+ } - if err := s.AddGeneratedConversionFunc((*SecretFileSource)(nil), (*v1beta1.SecretFileSource)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1alpha4_SecretFileSource_To_v1beta1_SecretFileSource(a.(*SecretFileSource), b.(*v1beta1.SecretFileSource), scope) - }); err != nil { -@@ -541,7 +581,43 @@ func Convert_v1beta1_BootstrapTokenString_To_v1alpha4_BootstrapTokenString(in *v - return autoConvert_v1beta1_BootstrapTokenString_To_v1alpha4_BootstrapTokenString(in, out, s) - } - -+func autoConvert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { -+ if err := Convert_v1alpha4_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap is an autogenerated conversion function. -+func Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { -+ return autoConvert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in, out, s) -+} -+ -+func autoConvert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { -+ if err := Convert_v1beta1_ImageMeta_To_v1alpha4_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap is an autogenerated conversion function. -+func Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { -+ return autoConvert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(in, out, s) -+} -+ - func autoConvert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *ClusterConfiguration, out *v1beta1.ClusterConfiguration, s conversion.Scope) error { -+ if err := Convert_v1alpha4_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_v1alpha4_Etcd_To_v1beta1_Etcd(&in.Etcd, &out.Etcd, s); err != nil { - return err - } -@@ -575,6 +651,18 @@ func Convert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *C - } - - func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(in *v1beta1.ClusterConfiguration, out *ClusterConfiguration, s conversion.Scope) error { -+ if err := Convert_v1beta1_Pause_To_v1alpha4_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_v1beta1_Etcd_To_v1alpha4_Etcd(&in.Etcd, &out.Etcd, s); err != nil { - return err - } -@@ -951,6 +1039,18 @@ func autoConvert_v1beta1_InitConfiguration_To_v1alpha4_InitConfiguration(in *v1b - } - - func autoConvert_v1alpha4_JoinConfiguration_To_v1beta1_JoinConfiguration(in *JoinConfiguration, out *v1beta1.JoinConfiguration, s conversion.Scope) error { -+ if err := Convert_v1alpha4_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_v1alpha4_NodeRegistrationOptions_To_v1beta1_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { - return err - } -@@ -968,6 +1068,18 @@ func Convert_v1alpha4_JoinConfiguration_To_v1beta1_JoinConfiguration(in *JoinCon - } - - func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1beta1.JoinConfiguration, out *JoinConfiguration, s conversion.Scope) error { -+ if err := Convert_v1beta1_Pause_To_v1alpha4_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_v1beta1_NodeRegistrationOptions_To_v1alpha4_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { - return err - } -@@ -1481,6 +1593,74 @@ func Convert_v1beta1_Partition_To_v1alpha4_Partition(in *v1beta1.Partition, out - return autoConvert_v1beta1_Partition_To_v1alpha4_Partition(in, out, s) - } - -+func autoConvert_v1alpha4_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { -+ if err := Convert_v1alpha4_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_v1alpha4_Pause_To_v1beta1_Pause is an autogenerated conversion function. -+func Convert_v1alpha4_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { -+ return autoConvert_v1alpha4_Pause_To_v1beta1_Pause(in, out, s) -+} -+ -+func autoConvert_v1beta1_Pause_To_v1alpha4_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { -+ if err := Convert_v1beta1_ImageMeta_To_v1alpha4_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_v1beta1_Pause_To_v1alpha4_Pause is an autogenerated conversion function. -+func Convert_v1beta1_Pause_To_v1alpha4_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { -+ return autoConvert_v1beta1_Pause_To_v1alpha4_Pause(in, out, s) -+} -+ -+func autoConvert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { -+ out.HTTPSProxy = in.HTTPSProxy -+ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) -+ return nil -+} -+ -+// Convert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration is an autogenerated conversion function. -+func Convert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { -+ return autoConvert_v1alpha4_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in, out, s) -+} -+ -+func autoConvert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { -+ out.HTTPSProxy = in.HTTPSProxy -+ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) -+ return nil -+} -+ -+// Convert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration is an autogenerated conversion function. -+func Convert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { -+ return autoConvert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(in, out, s) -+} -+ -+func autoConvert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { -+ out.Endpoint = in.Endpoint -+ out.CACert = in.CACert -+ return nil -+} -+ -+// Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration is an autogenerated conversion function. -+func Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { -+ return autoConvert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in, out, s) -+} -+ -+func autoConvert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { -+ out.Endpoint = in.Endpoint -+ out.CACert = in.CACert -+ return nil -+} -+ -+// Convert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration is an autogenerated conversion function. -+func Convert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { -+ return autoConvert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(in, out, s) -+} -+ - func autoConvert_v1alpha4_SecretFileSource_To_v1beta1_SecretFileSource(in *SecretFileSource, out *v1beta1.SecretFileSource, s conversion.Scope) error { - out.Name = in.Name - out.Key = in.Key -diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -index 9a40da3b2..ae1158152 100644 ---- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -@@ -88,6 +88,16 @@ func RegisterConversions(s *runtime.Scheme) error { - }); err != nil { - return err - } -+ if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrap)(nil), (*v1beta1.BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(a.(*BottlerocketBootstrap), b.(*v1beta1.BottlerocketBootstrap), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketBootstrap)(nil), (*BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(a.(*v1beta1.BottlerocketBootstrap), b.(*BottlerocketBootstrap), scope) -+ }); err != nil { -+ return err -+ } - if err := s.AddGeneratedConversionFunc((*v1beta1.ClusterConfiguration)(nil), (*ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1beta1_ClusterConfiguration_To_upstreamv1beta2_ClusterConfiguration(a.(*v1beta1.ClusterConfiguration), b.(*ClusterConfiguration), scope) - }); err != nil { -@@ -213,6 +223,36 @@ func RegisterConversions(s *runtime.Scheme) error { - }); err != nil { - return err - } -+ if err := s.AddGeneratedConversionFunc((*Pause)(nil), (*v1beta1.Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_upstreamv1beta2_Pause_To_v1beta1_Pause(a.(*Pause), b.(*v1beta1.Pause), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.Pause)(nil), (*Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_Pause_To_upstreamv1beta2_Pause(a.(*v1beta1.Pause), b.(*Pause), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*ProxyConfiguration)(nil), (*v1beta1.ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(a.(*ProxyConfiguration), b.(*v1beta1.ProxyConfiguration), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.ProxyConfiguration)(nil), (*ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(a.(*v1beta1.ProxyConfiguration), b.(*ProxyConfiguration), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*RegistryMirrorConfiguration)(nil), (*v1beta1.RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(a.(*RegistryMirrorConfiguration), b.(*v1beta1.RegistryMirrorConfiguration), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.RegistryMirrorConfiguration)(nil), (*RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(a.(*v1beta1.RegistryMirrorConfiguration), b.(*RegistryMirrorConfiguration), scope) -+ }); err != nil { -+ return err -+ } - if err := s.AddConversionFunc((*ClusterConfiguration)(nil), (*v1beta1.ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_upstreamv1beta2_ClusterConfiguration_To_v1beta1_ClusterConfiguration(a.(*ClusterConfiguration), b.(*v1beta1.ClusterConfiguration), scope) - }); err != nil { -@@ -379,7 +419,43 @@ func Convert_v1beta1_BootstrapTokenString_To_upstreamv1beta2_BootstrapTokenStrin - return autoConvert_v1beta1_BootstrapTokenString_To_upstreamv1beta2_BootstrapTokenString(in, out, s) - } - -+func autoConvert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { -+ if err := Convert_upstreamv1beta2_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap is an autogenerated conversion function. -+func Convert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { -+ return autoConvert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in, out, s) -+} -+ -+func autoConvert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { -+ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta2_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap is an autogenerated conversion function. -+func Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { -+ return autoConvert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(in, out, s) -+} -+ - func autoConvert_upstreamv1beta2_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *ClusterConfiguration, out *v1beta1.ClusterConfiguration, s conversion.Scope) error { -+ if err := Convert_upstreamv1beta2_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_upstreamv1beta2_Etcd_To_v1beta1_Etcd(&in.Etcd, &out.Etcd, s); err != nil { - return err - } -@@ -409,6 +485,18 @@ func autoConvert_upstreamv1beta2_ClusterConfiguration_To_v1beta1_ClusterConfigur - } - - func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta2_ClusterConfiguration(in *v1beta1.ClusterConfiguration, out *ClusterConfiguration, s conversion.Scope) error { -+ if err := Convert_v1beta1_Pause_To_upstreamv1beta2_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_v1beta1_Etcd_To_upstreamv1beta2_Etcd(&in.Etcd, &out.Etcd, s); err != nil { - return err - } -@@ -673,6 +761,18 @@ func autoConvert_v1beta1_InitConfiguration_To_upstreamv1beta2_InitConfiguration( - } - - func autoConvert_upstreamv1beta2_JoinConfiguration_To_v1beta1_JoinConfiguration(in *JoinConfiguration, out *v1beta1.JoinConfiguration, s conversion.Scope) error { -+ if err := Convert_upstreamv1beta2_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta2_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_upstreamv1beta2_NodeRegistrationOptions_To_v1beta1_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { - return err - } -@@ -698,6 +798,18 @@ func Convert_upstreamv1beta2_JoinConfiguration_To_v1beta1_JoinConfiguration(in * - } - - func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta2_JoinConfiguration(in *v1beta1.JoinConfiguration, out *JoinConfiguration, s conversion.Scope) error { -+ if err := Convert_v1beta1_Pause_To_upstreamv1beta2_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_v1beta1_NodeRegistrationOptions_To_upstreamv1beta2_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { - return err - } -@@ -818,3 +930,71 @@ func autoConvert_v1beta1_NodeRegistrationOptions_To_upstreamv1beta2_NodeRegistra - // WARNING: in.ImagePullPolicy requires manual conversion: does not exist in peer-type - return nil - } -+ -+func autoConvert_upstreamv1beta2_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { -+ if err := Convert_upstreamv1beta2_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_upstreamv1beta2_Pause_To_v1beta1_Pause is an autogenerated conversion function. -+func Convert_upstreamv1beta2_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { -+ return autoConvert_upstreamv1beta2_Pause_To_v1beta1_Pause(in, out, s) -+} -+ -+func autoConvert_v1beta1_Pause_To_upstreamv1beta2_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { -+ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta2_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_v1beta1_Pause_To_upstreamv1beta2_Pause is an autogenerated conversion function. -+func Convert_v1beta1_Pause_To_upstreamv1beta2_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { -+ return autoConvert_v1beta1_Pause_To_upstreamv1beta2_Pause(in, out, s) -+} -+ -+func autoConvert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { -+ out.HTTPSProxy = in.HTTPSProxy -+ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) -+ return nil -+} -+ -+// Convert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration is an autogenerated conversion function. -+func Convert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { -+ return autoConvert_upstreamv1beta2_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in, out, s) -+} -+ -+func autoConvert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { -+ out.HTTPSProxy = in.HTTPSProxy -+ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) -+ return nil -+} -+ -+// Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration is an autogenerated conversion function. -+func Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { -+ return autoConvert_v1beta1_ProxyConfiguration_To_upstreamv1beta2_ProxyConfiguration(in, out, s) -+} -+ -+func autoConvert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { -+ out.Endpoint = in.Endpoint -+ out.CACert = in.CACert -+ return nil -+} -+ -+// Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration is an autogenerated conversion function. -+func Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { -+ return autoConvert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in, out, s) -+} -+ -+func autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { -+ out.Endpoint = in.Endpoint -+ out.CACert = in.CACert -+ return nil -+} -+ -+// Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration is an autogenerated conversion function. -+func Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { -+ return autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(in, out, s) -+} -diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -index d849616cb..9b0c13356 100644 ---- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -@@ -88,6 +88,16 @@ func RegisterConversions(s *runtime.Scheme) error { - }); err != nil { - return err - } -+ if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrap)(nil), (*v1beta1.BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(a.(*BottlerocketBootstrap), b.(*v1beta1.BottlerocketBootstrap), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketBootstrap)(nil), (*BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(a.(*v1beta1.BottlerocketBootstrap), b.(*BottlerocketBootstrap), scope) -+ }); err != nil { -+ return err -+ } - if err := s.AddGeneratedConversionFunc((*ClusterConfiguration)(nil), (*v1beta1.ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_upstreamv1beta3_ClusterConfiguration_To_v1beta1_ClusterConfiguration(a.(*ClusterConfiguration), b.(*v1beta1.ClusterConfiguration), scope) - }); err != nil { -@@ -228,6 +238,36 @@ func RegisterConversions(s *runtime.Scheme) error { - }); err != nil { - return err - } -+ if err := s.AddGeneratedConversionFunc((*Pause)(nil), (*v1beta1.Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_upstreamv1beta3_Pause_To_v1beta1_Pause(a.(*Pause), b.(*v1beta1.Pause), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.Pause)(nil), (*Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_Pause_To_upstreamv1beta3_Pause(a.(*v1beta1.Pause), b.(*Pause), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*ProxyConfiguration)(nil), (*v1beta1.ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(a.(*ProxyConfiguration), b.(*v1beta1.ProxyConfiguration), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.ProxyConfiguration)(nil), (*ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(a.(*v1beta1.ProxyConfiguration), b.(*ProxyConfiguration), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*RegistryMirrorConfiguration)(nil), (*v1beta1.RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(a.(*RegistryMirrorConfiguration), b.(*v1beta1.RegistryMirrorConfiguration), scope) -+ }); err != nil { -+ return err -+ } -+ if err := s.AddGeneratedConversionFunc((*v1beta1.RegistryMirrorConfiguration)(nil), (*RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(a.(*v1beta1.RegistryMirrorConfiguration), b.(*RegistryMirrorConfiguration), scope) -+ }); err != nil { -+ return err -+ } - if err := s.AddConversionFunc((*InitConfiguration)(nil), (*v1beta1.InitConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_upstreamv1beta3_InitConfiguration_To_v1beta1_InitConfiguration(a.(*InitConfiguration), b.(*v1beta1.InitConfiguration), scope) - }); err != nil { -@@ -379,7 +419,43 @@ func Convert_v1beta1_BootstrapTokenString_To_upstreamv1beta3_BootstrapTokenStrin - return autoConvert_v1beta1_BootstrapTokenString_To_upstreamv1beta3_BootstrapTokenString(in, out, s) - } - -+func autoConvert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { -+ if err := Convert_upstreamv1beta3_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap is an autogenerated conversion function. -+func Convert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { -+ return autoConvert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in, out, s) -+} -+ -+func autoConvert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { -+ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta3_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap is an autogenerated conversion function. -+func Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { -+ return autoConvert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(in, out, s) -+} -+ - func autoConvert_upstreamv1beta3_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *ClusterConfiguration, out *v1beta1.ClusterConfiguration, s conversion.Scope) error { -+ if err := Convert_upstreamv1beta3_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_upstreamv1beta3_Etcd_To_v1beta1_Etcd(&in.Etcd, &out.Etcd, s); err != nil { - return err - } -@@ -413,6 +489,18 @@ func Convert_upstreamv1beta3_ClusterConfiguration_To_v1beta1_ClusterConfiguratio - } - - func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta3_ClusterConfiguration(in *v1beta1.ClusterConfiguration, out *ClusterConfiguration, s conversion.Scope) error { -+ if err := Convert_v1beta1_Pause_To_upstreamv1beta3_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_v1beta1_Etcd_To_upstreamv1beta3_Etcd(&in.Etcd, &out.Etcd, s); err != nil { - return err - } -@@ -668,6 +756,18 @@ func Convert_v1beta1_InitConfiguration_To_upstreamv1beta3_InitConfiguration(in * - } - - func autoConvert_upstreamv1beta3_JoinConfiguration_To_v1beta1_JoinConfiguration(in *JoinConfiguration, out *v1beta1.JoinConfiguration, s conversion.Scope) error { -+ if err := Convert_upstreamv1beta3_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta3_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_upstreamv1beta3_NodeRegistrationOptions_To_v1beta1_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { - return err - } -@@ -690,6 +790,18 @@ func autoConvert_upstreamv1beta3_JoinConfiguration_To_v1beta1_JoinConfiguration( - } - - func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta3_JoinConfiguration(in *v1beta1.JoinConfiguration, out *JoinConfiguration, s conversion.Scope) error { -+ if err := Convert_v1beta1_Pause_To_upstreamv1beta3_Pause(&in.Pause, &out.Pause, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { -+ return err -+ } -+ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { -+ return err -+ } - if err := Convert_v1beta1_NodeRegistrationOptions_To_upstreamv1beta3_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { - return err - } -@@ -836,3 +948,71 @@ func autoConvert_v1beta1_Patches_To_upstreamv1beta3_Patches(in *v1beta1.Patches, - func Convert_v1beta1_Patches_To_upstreamv1beta3_Patches(in *v1beta1.Patches, out *Patches, s conversion.Scope) error { - return autoConvert_v1beta1_Patches_To_upstreamv1beta3_Patches(in, out, s) - } -+ -+func autoConvert_upstreamv1beta3_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { -+ if err := Convert_upstreamv1beta3_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_upstreamv1beta3_Pause_To_v1beta1_Pause is an autogenerated conversion function. -+func Convert_upstreamv1beta3_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { -+ return autoConvert_upstreamv1beta3_Pause_To_v1beta1_Pause(in, out, s) -+} -+ -+func autoConvert_v1beta1_Pause_To_upstreamv1beta3_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { -+ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta3_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { -+ return err -+ } -+ return nil -+} -+ -+// Convert_v1beta1_Pause_To_upstreamv1beta3_Pause is an autogenerated conversion function. -+func Convert_v1beta1_Pause_To_upstreamv1beta3_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { -+ return autoConvert_v1beta1_Pause_To_upstreamv1beta3_Pause(in, out, s) -+} -+ -+func autoConvert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { -+ out.HTTPSProxy = in.HTTPSProxy -+ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) -+ return nil -+} -+ -+// Convert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration is an autogenerated conversion function. -+func Convert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { -+ return autoConvert_upstreamv1beta3_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in, out, s) -+} -+ -+func autoConvert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { -+ out.HTTPSProxy = in.HTTPSProxy -+ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) -+ return nil -+} -+ -+// Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration is an autogenerated conversion function. -+func Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { -+ return autoConvert_v1beta1_ProxyConfiguration_To_upstreamv1beta3_ProxyConfiguration(in, out, s) -+} -+ -+func autoConvert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { -+ out.Endpoint = in.Endpoint -+ out.CACert = in.CACert -+ return nil -+} -+ -+// Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration is an autogenerated conversion function. -+func Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { -+ return autoConvert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in, out, s) -+} -+ -+func autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { -+ out.Endpoint = in.Endpoint -+ out.CACert = in.CACert -+ return nil -+} -+ -+// Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration is an autogenerated conversion function. -+func Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { -+ return autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(in, out, s) -+} --- -2.39.3 (Apple Git-145) - diff --git a/projects/kubernetes-sigs/cluster-api/patches/0012-Add-node-labels-support-for-bottlerocket.patch b/projects/kubernetes-sigs/cluster-api/patches/0011-Add-node-labels-support-for-bottlerocket.patch similarity index 97% rename from projects/kubernetes-sigs/cluster-api/patches/0012-Add-node-labels-support-for-bottlerocket.patch rename to projects/kubernetes-sigs/cluster-api/patches/0011-Add-node-labels-support-for-bottlerocket.patch index 7a8fae52dd..cc5584519d 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0012-Add-node-labels-support-for-bottlerocket.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0011-Add-node-labels-support-for-bottlerocket.patch @@ -1,7 +1,7 @@ -From 080efb5b27eee08692b85d9aacef6aad8221a016 Mon Sep 17 00:00:00 2001 +From 5b15eaf1d7bf84063f80765324c3886996897cbd Mon Sep 17 00:00:00 2001 From: Vivek Koppuru Date: Mon, 24 Jan 2022 00:46:44 -0800 -Subject: [PATCH 12/40] Add node labels support for bottlerocket +Subject: [PATCH 11/40] Add node labels support for bottlerocket --- .../internal/bottlerocket/bootstrap.go | 9 ++++++++ @@ -130,5 +130,5 @@ index cbc236823..97376f758 100644 if err != nil { scope.Error(err, "Failed to generate cloud init for bottlerocket bootstrap control plane") -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0013-Support-worker-node-taints.patch b/projects/kubernetes-sigs/cluster-api/patches/0012-Support-worker-node-taints.patch similarity index 97% rename from projects/kubernetes-sigs/cluster-api/patches/0013-Support-worker-node-taints.patch rename to projects/kubernetes-sigs/cluster-api/patches/0012-Support-worker-node-taints.patch index d3b538b66c..7780ed29c0 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0013-Support-worker-node-taints.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0012-Support-worker-node-taints.patch @@ -1,7 +1,7 @@ -From 89876dd9741747a7f306e44fc48da2c1a0cdf0a9 Mon Sep 17 00:00:00 2001 +From ecfdde4fd678977cd76907d54b4be21167f80daf Mon Sep 17 00:00:00 2001 From: Daniel Budris Date: Fri, 17 Dec 2021 13:38:39 -0800 -Subject: [PATCH 13/40] Support worker node taints +Subject: [PATCH 12/40] Support worker node taints seperate taints template into its own template @@ -143,5 +143,5 @@ index 97376f758..5ea943c27 100644 if err != nil { scope.Error(err, "Failed to create a worker bottlerocket join configuration") -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0014-support-bottle-rocket-control-plane-taints.patch b/projects/kubernetes-sigs/cluster-api/patches/0013-support-bottle-rocket-control-plane-taints.patch similarity index 92% rename from projects/kubernetes-sigs/cluster-api/patches/0014-support-bottle-rocket-control-plane-taints.patch rename to projects/kubernetes-sigs/cluster-api/patches/0013-support-bottle-rocket-control-plane-taints.patch index 26aad33bd4..61684138fe 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0014-support-bottle-rocket-control-plane-taints.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0013-support-bottle-rocket-control-plane-taints.patch @@ -1,7 +1,7 @@ -From 737a1b8fc2bea159b2c37c95513e12c28fcb0930 Mon Sep 17 00:00:00 2001 +From ca85c8ede9cc798059c76dcb51f7a0ae41aed087 Mon Sep 17 00:00:00 2001 From: danbudris Date: Fri, 18 Feb 2022 09:24:32 -0500 -Subject: [PATCH 14/40] support bottle rocket control plane taints +Subject: [PATCH 13/40] support bottle rocket control plane taints --- .../internal/controllers/kubeadmconfig_controller.go | 6 ++++++ @@ -32,5 +32,5 @@ index 5ea943c27..1cc21be4b 100644 if err != nil { scope.Error(err, "Failed to generate cloud init for bottlerocket bootstrap control plane") -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0015-Support-configuring-bottlerocket-control-container-u.patch b/projects/kubernetes-sigs/cluster-api/patches/0014-Support-configuring-bottlerocket-control-container-u.patch similarity index 57% rename from projects/kubernetes-sigs/cluster-api/patches/0015-Support-configuring-bottlerocket-control-container-u.patch rename to projects/kubernetes-sigs/cluster-api/patches/0014-Support-configuring-bottlerocket-control-container-u.patch index 797b9926e3..811a3f3048 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0015-Support-configuring-bottlerocket-control-container-u.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0014-Support-configuring-bottlerocket-control-container-u.patch @@ -1,69 +1,37 @@ -From f4c7903721aa4685ae33314fd088693beec58f63 Mon Sep 17 00:00:00 2001 +From f20a0f56cf88953eebc1828ad7da9e085c6c5110 Mon Sep 17 00:00:00 2001 From: Michael Chu Date: Mon, 28 Feb 2022 09:51:25 -0800 -Subject: [PATCH 15/40] Support configuring bottlerocket control container uri +Subject: [PATCH 14/40] Support configuring bottlerocket control container uri Signed-off-by: Michael Chu --- - api/v1alpha4/zz_generated.deepcopy.go | 5 + - api/v1beta1/zz_generated.deepcopy.go | 5 + - .../kubeadm/api/v1alpha4/kubeadm_types.go | 17 ++++ - .../api/v1alpha4/zz_generated.conversion.go | 46 +++++++++ - .../api/v1alpha4/zz_generated.deepcopy.go | 18 ++++ - .../kubeadm/api/v1beta1/kubeadm_types.go | 17 ++++ - .../api/v1beta1/zz_generated.deepcopy.go | 18 ++++ - ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 60 ++++++++++++ - ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 64 +++++++++++++ - .../internal/bottlerocket/bootstrap.go | 12 +++ - .../internal/bottlerocket/bottlerocket.go | 8 ++ - .../controllers/kubeadmconfig_controller.go | 2 + - .../kubeadm/types/upstreamv1beta2/types.go | 17 ++++ - .../zz_generated.conversion.go | 46 +++++++++ - .../upstreamv1beta2/zz_generated.deepcopy.go | 93 +++++++++++++++++++ - .../kubeadm/types/upstreamv1beta3/types.go | 17 ++++ - .../zz_generated.conversion.go | 46 +++++++++ - .../upstreamv1beta3/zz_generated.deepcopy.go | 93 +++++++++++++++++++ - bootstrap/kubeadm/types/utils_test.go | 34 ++++++- - cmd/clusterctl/client/cluster/mover_test.go | 6 +- - ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 64 +++++++++++++ - ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 68 ++++++++++++++ - .../internal/workload_cluster_coredns_test.go | 5 + - .../internal/workload_cluster_etcd_test.go | 10 ++ - .../kubeadm/internal/workload_cluster_test.go | 25 +++++ - 25 files changed, 791 insertions(+), 5 deletions(-) + .../kubeadm/api/v1alpha4/kubeadm_types.go | 17 + + .../api/v1alpha4/zz_generated.conversion.go | 46 +++ + .../api/v1alpha4/zz_generated.deepcopy.go | 18 ++ + .../kubeadm/api/v1beta1/kubeadm_types.go | 17 + + .../api/v1beta1/zz_generated.deepcopy.go | 18 ++ + ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 282 +++++++++++++--- + ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 302 +++++++++++++++--- + .../internal/bottlerocket/bootstrap.go | 12 + + .../internal/bottlerocket/bottlerocket.go | 8 + + .../controllers/kubeadmconfig_controller.go | 3 + + .../kubeadm/types/upstreamv1beta1/types.go | 17 + + .../upstreamv1beta1/zz_generated.deepcopy.go | 18 ++ + .../kubeadm/types/upstreamv1beta2/types.go | 17 + + .../zz_generated.conversion.go | 46 +++ + .../upstreamv1beta2/zz_generated.deepcopy.go | 18 ++ + .../kubeadm/types/upstreamv1beta3/types.go | 17 + + .../zz_generated.conversion.go | 46 +++ + .../upstreamv1beta3/zz_generated.deepcopy.go | 18 ++ + bootstrap/kubeadm/types/utils_test.go | 34 +- + cmd/clusterctl/client/cluster/mover_test.go | 6 +- + ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 302 +++++++++++++++--- + ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 68 ++++ + .../internal/workload_cluster_coredns_test.go | 5 + + .../internal/workload_cluster_etcd_test.go | 10 + + .../kubeadm/internal/workload_cluster_test.go | 25 ++ + 25 files changed, 1236 insertions(+), 134 deletions(-) -diff --git a/api/v1alpha4/zz_generated.deepcopy.go b/api/v1alpha4/zz_generated.deepcopy.go -index ac1ae21e3..7aa525c07 100644 ---- a/api/v1alpha4/zz_generated.deepcopy.go -+++ b/api/v1alpha4/zz_generated.deepcopy.go -@@ -247,6 +247,11 @@ func (in *ClusterSpec) DeepCopyInto(out *ClusterSpec) { - *out = new(v1.ObjectReference) - **out = **in - } -+ if in.ManagedExternalEtcdRef != nil { -+ in, out := &in.ManagedExternalEtcdRef, &out.ManagedExternalEtcdRef -+ *out = new(v1.ObjectReference) -+ **out = **in -+ } - if in.InfrastructureRef != nil { - in, out := &in.InfrastructureRef, &out.InfrastructureRef - *out = new(v1.ObjectReference) -diff --git a/api/v1beta1/zz_generated.deepcopy.go b/api/v1beta1/zz_generated.deepcopy.go -index 7eb964845..5629c4a37 100644 ---- a/api/v1beta1/zz_generated.deepcopy.go -+++ b/api/v1beta1/zz_generated.deepcopy.go -@@ -378,6 +378,11 @@ func (in *ClusterSpec) DeepCopyInto(out *ClusterSpec) { - *out = new(v1.ObjectReference) - **out = **in - } -+ if in.ManagedExternalEtcdRef != nil { -+ in, out := &in.ManagedExternalEtcdRef, &out.ManagedExternalEtcdRef -+ *out = new(v1.ObjectReference) -+ **out = **in -+ } - if in.InfrastructureRef != nil { - in, out := &in.InfrastructureRef, &out.InfrastructureRef - *out = new(v1.ObjectReference) diff --git a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go index 29df78f5c..9027f336f 100644 --- a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go @@ -325,10 +293,10 @@ index 90c8c89be..80d9362bb 100644 out.RegistryMirror = in.RegistryMirror in.NodeRegistration.DeepCopyInto(&out.NodeRegistration) diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -index 5baf0eb85..e0ca0a0ca 100644 +index ab6e724ca..f0e8338be 100644 --- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -@@ -123,6 +123,21 @@ spec: +@@ -118,6 +118,21 @@ spec: the version of the above components during upgrades. type: string type: object @@ -350,7 +318,15 @@ index 5baf0eb85..e0ca0a0ca 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, this will -@@ -732,6 +747,21 @@ spec: +@@ -550,7 +565,6 @@ spec: + description: Format specifies the output format of the bootstrap data + enum: + - cloud-config +- - bottlerocket + type: string + initConfiguration: + description: InitConfiguration along with ClusterConfiguration are +@@ -732,6 +746,21 @@ spec: the version of the above components during upgrades. type: string type: object @@ -372,7 +348,7 @@ index 5baf0eb85..e0ca0a0ca 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node and control-plane. -@@ -1222,6 +1252,21 @@ spec: +@@ -1224,6 +1253,21 @@ spec: the version of the above components during upgrades. type: string type: object @@ -394,7 +370,15 @@ index 5baf0eb85..e0ca0a0ca 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, this will -@@ -1900,6 +1945,21 @@ spec: +@@ -1648,6 +1692,7 @@ spec: + description: Format specifies the output format of the bootstrap data + enum: + - cloud-config ++ - bottlerocket + type: string + initConfiguration: + description: InitConfiguration along with ClusterConfiguration are +@@ -1832,6 +1877,21 @@ spec: the version of the above components during upgrades. type: string type: object @@ -416,11 +400,273 @@ index 5baf0eb85..e0ca0a0ca 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node and control-plane. +@@ -2003,6 +2063,46 @@ spec: + type: object + type: array + type: object ++ pause: ++ description: Pause holds the image source for pause container ++ This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object ++ proxy: ++ description: Proxy holds the https and no proxy information This ++ is only for bottlerocket ++ properties: ++ httpsProxy: ++ description: HTTPS proxy ++ type: string ++ noProxy: ++ description: No proxy, list of ips that should not use proxy ++ items: ++ type: string ++ type: array ++ type: object ++ registryMirror: ++ description: RegistryMirror holds the image registry mirror information ++ This is only for bottlerocket ++ properties: ++ caCert: ++ description: CACert defines the CA cert for the registry mirror ++ type: string ++ endpoint: ++ description: Endpoint defines the registry mirror endpoint ++ to use for pulling images ++ type: string ++ type: object + type: object + mounts: + description: Mounts specifies a list of mount points to be setup. +@@ -2267,6 +2367,36 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketBootstrap: ++ description: BottlerocketBootstrap holds the image source for ++ kubeadm bootstrap container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object ++ bottlerocketControl: ++ description: BottlerocketControl holds the image source for control ++ container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object + certificatesDir: + description: 'CertificatesDir specifies where to store or look + for all required certificates. NB: if not provided, this will +@@ -2473,6 +2603,46 @@ spec: + if that's unset. + type: string + type: object ++ pause: ++ description: Pause holds the image source for pause container ++ This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object ++ proxy: ++ description: Proxy holds the https and no proxy information This ++ is only for bottlerocket ++ properties: ++ httpsProxy: ++ description: HTTPS proxy ++ type: string ++ noProxy: ++ description: No proxy, list of ips that should not use proxy ++ items: ++ type: string ++ type: array ++ type: object ++ registryMirror: ++ description: RegistryMirror holds the image registry mirror information ++ This is only for bottlerocket ++ properties: ++ caCert: ++ description: CACert defines the CA cert for the registry mirror ++ type: string ++ endpoint: ++ description: Endpoint defines the registry mirror endpoint ++ to use for pulling images ++ type: string ++ type: object + scheduler: + description: Scheduler contains extra settings for the scheduler + control plane component +@@ -2871,46 +3041,6 @@ spec: + content inline or by referencing a secret. + type: string + type: object +- pause: +- description: Pause holds the image source for pause container +- This is only for bottlerocket +- properties: +- imageRepository: +- description: ImageRepository sets the container registry to +- pull images from. if not set, the ImageRepository defined +- in ClusterConfiguration will be used instead. +- type: string +- imageTag: +- description: ImageTag allows to specify a tag for the image. +- In case this value is set, kubeadm does not change automatically +- the version of the above components during upgrades. +- type: string +- type: object +- proxy: +- description: Proxy holds the https and no proxy information This +- is only for bottlerocket +- properties: +- httpsProxy: +- description: HTTPS proxy +- type: string +- noProxy: +- description: No proxy, list of ips that should not use proxy +- items: +- type: string +- type: array +- type: object +- registryMirror: +- description: RegistryMirror holds the image registry mirror information +- This is only for bottlerocket +- properties: +- caCert: +- description: CACert defines the CA cert for the registry mirror +- type: string +- endpoint: +- description: Endpoint defines the registry mirror endpoint +- to use for pulling images +- type: string +- type: object + skipPhases: + description: SkipPhases is a list of phases to skip during command + execution. The list of phases can be obtained with the "kubeadm +@@ -2930,6 +3060,36 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketBootstrap: ++ description: BottlerocketBootstrap holds the image source for ++ kubeadm bootstrap container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object ++ bottlerocketControl: ++ description: BottlerocketControl holds the image source for control ++ container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object + caCertPath: + description: 'CACertPath is the path to the SSL certificate authority + used to secure comunications between node and control-plane. +@@ -3133,6 +3293,46 @@ spec: + content inline or by referencing a secret. + type: string + type: object ++ pause: ++ description: Pause holds the image source for pause container ++ This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object ++ proxy: ++ description: Proxy holds the https and no proxy information This ++ is only for bottlerocket ++ properties: ++ httpsProxy: ++ description: HTTPS proxy ++ type: string ++ noProxy: ++ description: No proxy, list of ips that should not use proxy ++ items: ++ type: string ++ type: array ++ type: object ++ registryMirror: ++ description: RegistryMirror holds the image registry mirror information ++ This is only for bottlerocket ++ properties: ++ caCert: ++ description: CACert defines the CA cert for the registry mirror ++ type: string ++ endpoint: ++ description: Endpoint defines the registry mirror endpoint ++ to use for pulling images ++ type: string ++ type: object + skipPhases: + description: SkipPhases is a list of phases to skip during command + execution. The list of phases can be obtained with the "kubeadm diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -index a1974c4c9..606155b09 100644 +index bdf596e4c..6586d0dbf 100644 --- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -@@ -132,6 +132,22 @@ spec: +@@ -127,6 +127,22 @@ spec: components during upgrades. type: string type: object @@ -443,7 +689,15 @@ index a1974c4c9..606155b09 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, -@@ -781,6 +797,22 @@ spec: +@@ -586,7 +602,6 @@ spec: + data + enum: + - cloud-config +- - bottlerocket + type: string + initConfiguration: + description: InitConfiguration along with ClusterConfiguration +@@ -779,6 +794,22 @@ spec: components during upgrades. type: string type: object @@ -466,7 +720,7 @@ index a1974c4c9..606155b09 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node -@@ -1254,6 +1286,22 @@ spec: +@@ -1229,6 +1260,22 @@ spec: components during upgrades. type: string type: object @@ -489,7 +743,15 @@ index a1974c4c9..606155b09 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, -@@ -1980,6 +2028,22 @@ spec: +@@ -1681,6 +1728,7 @@ spec: + data + enum: + - cloud-config ++ - bottlerocket + type: string + initConfiguration: + description: InitConfiguration along with ClusterConfiguration +@@ -1877,6 +1925,22 @@ spec: components during upgrades. type: string type: object @@ -512,6 +774,284 @@ index a1974c4c9..606155b09 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node +@@ -2060,6 +2124,49 @@ spec: + type: object + type: array + type: object ++ pause: ++ description: Pause holds the image source for pause container ++ This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object ++ proxy: ++ description: Proxy holds the https and no proxy information ++ This is only for bottlerocket ++ properties: ++ httpsProxy: ++ description: HTTPS proxy ++ type: string ++ noProxy: ++ description: No proxy, list of ips that should not ++ use proxy ++ items: ++ type: string ++ type: array ++ type: object ++ registryMirror: ++ description: RegistryMirror holds the image registry mirror ++ information This is only for bottlerocket ++ properties: ++ caCert: ++ description: CACert defines the CA cert for the registry ++ mirror ++ type: string ++ endpoint: ++ description: Endpoint defines the registry mirror ++ endpoint to use for pulling images ++ type: string ++ type: object + type: object + mounts: + description: Mounts specifies a list of mount points to be +@@ -2291,6 +2398,38 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketBootstrap: ++ description: BottlerocketBootstrap holds the image source ++ for kubeadm bootstrap container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object ++ bottlerocketControl: ++ description: BottlerocketControl holds the image source ++ for control container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object + certificatesDir: + description: 'CertificatesDir specifies where to store + or look for all required certificates. NB: if not provided, +@@ -2512,6 +2651,49 @@ spec: + or to "10.96.0.0/12" if that's unset. + type: string + type: object ++ pause: ++ description: Pause holds the image source for pause container ++ This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object ++ proxy: ++ description: Proxy holds the https and no proxy information ++ This is only for bottlerocket ++ properties: ++ httpsProxy: ++ description: HTTPS proxy ++ type: string ++ noProxy: ++ description: No proxy, list of ips that should not ++ use proxy ++ items: ++ type: string ++ type: array ++ type: object ++ registryMirror: ++ description: RegistryMirror holds the image registry mirror ++ information This is only for bottlerocket ++ properties: ++ caCert: ++ description: CACert defines the CA cert for the registry ++ mirror ++ type: string ++ endpoint: ++ description: Endpoint defines the registry mirror ++ endpoint to use for pulling images ++ type: string ++ type: object + scheduler: + description: Scheduler contains extra settings for the + scheduler control plane component +@@ -2939,49 +3121,6 @@ spec: + content inline or by referencing a secret. + type: string + type: object +- pause: +- description: Pause holds the image source for pause container +- This is only for bottlerocket +- properties: +- imageRepository: +- description: ImageRepository sets the container registry +- to pull images from. if not set, the ImageRepository +- defined in ClusterConfiguration will be used instead. +- type: string +- imageTag: +- description: ImageTag allows to specify a tag for +- the image. In case this value is set, kubeadm does +- not change automatically the version of the above +- components during upgrades. +- type: string +- type: object +- proxy: +- description: Proxy holds the https and no proxy information +- This is only for bottlerocket +- properties: +- httpsProxy: +- description: HTTPS proxy +- type: string +- noProxy: +- description: No proxy, list of ips that should not +- use proxy +- items: +- type: string +- type: array +- type: object +- registryMirror: +- description: RegistryMirror holds the image registry mirror +- information This is only for bottlerocket +- properties: +- caCert: +- description: CACert defines the CA cert for the registry +- mirror +- type: string +- endpoint: +- description: Endpoint defines the registry mirror +- endpoint to use for pulling images +- type: string +- type: object + skipPhases: + description: SkipPhases is a list of phases to skip during + command execution. The list of phases can be obtained +@@ -3001,6 +3140,38 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketBootstrap: ++ description: BottlerocketBootstrap holds the image source ++ for kubeadm bootstrap container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object ++ bottlerocketControl: ++ description: BottlerocketControl holds the image source ++ for control container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object + caCertPath: + description: 'CACertPath is the path to the SSL certificate + authority used to secure comunications between node +@@ -3220,6 +3391,49 @@ spec: + content inline or by referencing a secret. + type: string + type: object ++ pause: ++ description: Pause holds the image source for pause container ++ This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object ++ proxy: ++ description: Proxy holds the https and no proxy information ++ This is only for bottlerocket ++ properties: ++ httpsProxy: ++ description: HTTPS proxy ++ type: string ++ noProxy: ++ description: No proxy, list of ips that should not ++ use proxy ++ items: ++ type: string ++ type: array ++ type: object ++ registryMirror: ++ description: RegistryMirror holds the image registry mirror ++ information This is only for bottlerocket ++ properties: ++ caCert: ++ description: CACert defines the CA cert for the registry ++ mirror ++ type: string ++ endpoint: ++ description: Endpoint defines the registry mirror ++ endpoint to use for pulling images ++ type: string ++ type: object + skipPhases: + description: SkipPhases is a list of phases to skip during + command execution. The list of phases can be obtained diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go index dd769a78d..f8f1b97cb 100644 --- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go @@ -582,7 +1122,7 @@ index fd3c9d15d..833f2d1c6 100644 for _, noProxy := range config.ProxyConfiguration.NoProxy { bottlerocketInput.NoProxyEndpoints = append(bottlerocketInput.NoProxyEndpoints, strconv.Quote(noProxy)) diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -index 1cc21be4b..d5dc72b76 100644 +index 1cc21be4b..fd96264ea 100644 --- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go +++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go @@ -475,6 +475,7 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex @@ -601,6 +1141,98 @@ index 1cc21be4b..d5dc72b76 100644 } if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy +@@ -805,6 +807,7 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S + bottlerocketConfig := &bottlerocket.BottlerocketConfig{ + Pause: scope.Config.Spec.JoinConfiguration.Pause, + BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, ++ BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, + } + if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { + bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/types.go b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +index 8fe3ee5ae..6ac8e40d4 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/types.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +@@ -65,6 +65,11 @@ type ClusterConfiguration struct { + // +optional + BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` + ++ // BottlerocketControl holds the image source for control container ++ // This is only for bottlerocket ++ // +optional ++ BottlerocketControl BottlerocketControl `json:"bottlerocketControl,omitempty"` ++ + // Proxy holds the https and no proxy information + // This is only for bottlerocket + // +optional +@@ -160,6 +165,13 @@ type BottlerocketBootstrap struct { + ImageMeta `json:",inline"` + } + ++// BottlerocketControl holds the settings of control container for bottlerocket nodes ++// This setting is ONLY for bottlerocket nodes. ++type BottlerocketControl struct { ++ // ImageMeta allows to customize the image used for the BottlerocketControl component ++ ImageMeta `json:",inline"` ++} ++ + // ProxyConfiguration holds the settings for proxying bottlerocket services + type ProxyConfiguration struct { + // HTTPS proxy +@@ -389,6 +401,11 @@ type JoinConfiguration struct { + // +optional + BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` + ++ // BottlerocketControl holds the image source for control container ++ // This is only for bottlerocket ++ // +optional ++ BottlerocketControl BottlerocketControl `json:"bottlerocketControl,omitempty"` ++ + // Proxy holds the https and no proxy information + // This is only for bottlerocket + // +optional +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +index 258534eb0..a48491019 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +@@ -157,12 +157,29 @@ func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketControl) DeepCopyInto(out *BottlerocketControl) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketControl. ++func (in *BottlerocketControl) DeepCopy() *BottlerocketControl { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketControl) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = *in + out.TypeMeta = in.TypeMeta + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror + in.Etcd.DeepCopyInto(&out.Etcd) +@@ -431,6 +448,7 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + out.TypeMeta = in.TypeMeta + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror + in.NodeRegistration.DeepCopyInto(&out.NodeRegistration) diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/types.go b/bootstrap/kubeadm/types/upstreamv1beta2/types.go index ff9a01d04..b45040a22 100644 --- a/bootstrap/kubeadm/types/upstreamv1beta2/types.go @@ -736,29 +1368,13 @@ index ae1158152..a0d3f763c 100644 return err } diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.deepcopy.go -index c4cecbaad..4314a802a 100644 +index 1caece2f9..4314a802a 100644 --- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.deepcopy.go +++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.deepcopy.go -@@ -141,10 +141,47 @@ func (in *BootstrapTokenString) DeepCopy() *BootstrapTokenString { +@@ -157,12 +157,29 @@ func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { return out } -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { -+ *out = *in -+ out.ImageMeta = in.ImageMeta -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootstrap. -+func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { -+ if in == nil { -+ return nil -+ } -+ out := new(BottlerocketBootstrap) -+ in.DeepCopyInto(out) -+ return out -+} -+ +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *BottlerocketControl) DeepCopyInto(out *BottlerocketControl) { + *out = *in @@ -779,81 +1395,20 @@ index c4cecbaad..4314a802a 100644 func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { *out = *in out.TypeMeta = in.TypeMeta -+ out.Pause = in.Pause -+ out.BottlerocketBootstrap = in.BottlerocketBootstrap + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap + out.BottlerocketControl = in.BottlerocketControl -+ in.Proxy.DeepCopyInto(&out.Proxy) -+ out.RegistryMirror = in.RegistryMirror + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror in.Etcd.DeepCopyInto(&out.Etcd) - out.Networking = in.Networking - in.APIServer.DeepCopyInto(&out.APIServer) -@@ -409,6 +446,11 @@ func (in *InitConfiguration) DeepCopyObject() runtime.Object { - func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { - *out = *in +@@ -431,6 +448,7 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { out.TypeMeta = in.TypeMeta -+ out.Pause = in.Pause -+ out.BottlerocketBootstrap = in.BottlerocketBootstrap + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap + out.BottlerocketControl = in.BottlerocketControl -+ in.Proxy.DeepCopyInto(&out.Proxy) -+ out.RegistryMirror = in.RegistryMirror + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror in.NodeRegistration.DeepCopyInto(&out.NodeRegistration) - in.Discovery.DeepCopyInto(&out.Discovery) - if in.ControlPlane != nil { -@@ -533,3 +575,54 @@ func (in *NodeRegistrationOptions) DeepCopy() *NodeRegistrationOptions { - in.DeepCopyInto(out) - return out - } -+ -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *Pause) DeepCopyInto(out *Pause) { -+ *out = *in -+ out.ImageMeta = in.ImageMeta -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Pause. -+func (in *Pause) DeepCopy() *Pause { -+ if in == nil { -+ return nil -+ } -+ out := new(Pause) -+ in.DeepCopyInto(out) -+ return out -+} -+ -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *ProxyConfiguration) DeepCopyInto(out *ProxyConfiguration) { -+ *out = *in -+ if in.NoProxy != nil { -+ in, out := &in.NoProxy, &out.NoProxy -+ *out = make([]string, len(*in)) -+ copy(*out, *in) -+ } -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ProxyConfiguration. -+func (in *ProxyConfiguration) DeepCopy() *ProxyConfiguration { -+ if in == nil { -+ return nil -+ } -+ out := new(ProxyConfiguration) -+ in.DeepCopyInto(out) -+ return out -+} -+ -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *RegistryMirrorConfiguration) DeepCopyInto(out *RegistryMirrorConfiguration) { -+ *out = *in -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new RegistryMirrorConfiguration. -+func (in *RegistryMirrorConfiguration) DeepCopy() *RegistryMirrorConfiguration { -+ if in == nil { -+ return nil -+ } -+ out := new(RegistryMirrorConfiguration) -+ in.DeepCopyInto(out) -+ return out -+} diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/types.go b/bootstrap/kubeadm/types/upstreamv1beta3/types.go index 42bda5ca0..ea1301706 100644 --- a/bootstrap/kubeadm/types/upstreamv1beta3/types.go @@ -989,29 +1544,13 @@ index 9b0c13356..197c2ef74 100644 return err } diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.deepcopy.go -index 77bc8ac51..baa2867cb 100644 +index b7b976a49..baa2867cb 100644 --- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.deepcopy.go +++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.deepcopy.go -@@ -141,10 +141,47 @@ func (in *BootstrapTokenString) DeepCopy() *BootstrapTokenString { +@@ -157,12 +157,29 @@ func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { return out } -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { -+ *out = *in -+ out.ImageMeta = in.ImageMeta -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootstrap. -+func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { -+ if in == nil { -+ return nil -+ } -+ out := new(BottlerocketBootstrap) -+ in.DeepCopyInto(out) -+ return out -+} -+ +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *BottlerocketControl) DeepCopyInto(out *BottlerocketControl) { + *out = *in @@ -1032,81 +1571,20 @@ index 77bc8ac51..baa2867cb 100644 func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { *out = *in out.TypeMeta = in.TypeMeta -+ out.Pause = in.Pause -+ out.BottlerocketBootstrap = in.BottlerocketBootstrap + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap + out.BottlerocketControl = in.BottlerocketControl -+ in.Proxy.DeepCopyInto(&out.Proxy) -+ out.RegistryMirror = in.RegistryMirror + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror in.Etcd.DeepCopyInto(&out.Etcd) - out.Networking = in.Networking - in.APIServer.DeepCopyInto(&out.APIServer) -@@ -388,6 +425,11 @@ func (in *InitConfiguration) DeepCopyObject() runtime.Object { - func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { - *out = *in +@@ -410,6 +427,7 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { out.TypeMeta = in.TypeMeta -+ out.Pause = in.Pause -+ out.BottlerocketBootstrap = in.BottlerocketBootstrap + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap + out.BottlerocketControl = in.BottlerocketControl -+ in.Proxy.DeepCopyInto(&out.Proxy) -+ out.RegistryMirror = in.RegistryMirror + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror in.NodeRegistration.DeepCopyInto(&out.NodeRegistration) - in.Discovery.DeepCopyInto(&out.Discovery) - if in.ControlPlane != nil { -@@ -537,3 +579,54 @@ func (in *Patches) DeepCopy() *Patches { - in.DeepCopyInto(out) - return out - } -+ -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *Pause) DeepCopyInto(out *Pause) { -+ *out = *in -+ out.ImageMeta = in.ImageMeta -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Pause. -+func (in *Pause) DeepCopy() *Pause { -+ if in == nil { -+ return nil -+ } -+ out := new(Pause) -+ in.DeepCopyInto(out) -+ return out -+} -+ -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *ProxyConfiguration) DeepCopyInto(out *ProxyConfiguration) { -+ *out = *in -+ if in.NoProxy != nil { -+ in, out := &in.NoProxy, &out.NoProxy -+ *out = make([]string, len(*in)) -+ copy(*out, *in) -+ } -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ProxyConfiguration. -+func (in *ProxyConfiguration) DeepCopy() *ProxyConfiguration { -+ if in == nil { -+ return nil -+ } -+ out := new(ProxyConfiguration) -+ in.DeepCopyInto(out) -+ return out -+} -+ -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *RegistryMirrorConfiguration) DeepCopyInto(out *RegistryMirrorConfiguration) { -+ *out = *in -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new RegistryMirrorConfiguration. -+func (in *RegistryMirrorConfiguration) DeepCopy() *RegistryMirrorConfiguration { -+ if in == nil { -+ return nil -+ } -+ out := new(RegistryMirrorConfiguration) -+ in.DeepCopyInto(out) -+ return out -+} diff --git a/bootstrap/kubeadm/types/utils_test.go b/bootstrap/kubeadm/types/utils_test.go index 49c9450b9..ae560aa39 100644 --- a/bootstrap/kubeadm/types/utils_test.go @@ -1244,10 +1722,10 @@ index b4100b007..dee567918 100644 "Secret_ns2_bar-ca.yaml": `{"apiVersion":"v1","kind":"Secret","metadata":{"creationTimestamp":null,"name":"bar-ca","namespace":"ns2","resourceVersion":"999","uid":"/v1, Kind=Secret, ns2/bar-ca"}}` + "\n", "GenericInfrastructureCluster_ns2_bar.yaml": `{"apiVersion":"infrastructure.cluster.x-k8s.io/v1beta1","kind":"GenericInfrastructureCluster","metadata":{"creationTimestamp":null,"labels":{"cluster.x-k8s.io/cluster-name":"bar"},"name":"bar","namespace":"ns2","ownerReferences":[{"apiVersion":"cluster.x-k8s.io/v1beta1","kind":"Cluster","name":"bar","uid":"cluster.x-k8s.io/v1beta1, Kind=Cluster, ns2/bar"}],"resourceVersion":"999","uid":"infrastructure.cluster.x-k8s.io/v1beta1, Kind=GenericInfrastructureCluster, ns2/bar"}}` + "\n", diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -index a0ee31f83..6aba94af6 100644 +index 0e19a7e4a..b207309b9 100644 --- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -@@ -160,6 +160,22 @@ spec: +@@ -194,6 +194,22 @@ spec: upgrades. type: string type: object @@ -1270,7 +1748,15 @@ index a0ee31f83..6aba94af6 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, -@@ -793,6 +809,22 @@ spec: +@@ -642,7 +658,6 @@ spec: + data + enum: + - cloud-config +- - bottlerocket + type: string + initConfiguration: + description: InitConfiguration along with ClusterConfiguration +@@ -831,6 +846,22 @@ spec: upgrades. type: string type: object @@ -1293,7 +1779,7 @@ index a0ee31f83..6aba94af6 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node and -@@ -1499,6 +1531,22 @@ spec: +@@ -1453,6 +1484,22 @@ spec: upgrades. type: string type: object @@ -1316,7 +1802,15 @@ index a0ee31f83..6aba94af6 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, -@@ -2205,6 +2253,22 @@ spec: +@@ -1893,6 +1940,7 @@ spec: + data + enum: + - cloud-config ++ - bottlerocket + type: string + initConfiguration: + description: InitConfiguration along with ClusterConfiguration +@@ -2085,6 +2133,22 @@ spec: upgrades. type: string type: object @@ -1339,6 +1833,284 @@ index a0ee31f83..6aba94af6 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node and +@@ -2263,6 +2327,49 @@ spec: + type: object + type: array + type: object ++ pause: ++ description: Pause holds the image source for pause container ++ This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object ++ proxy: ++ description: Proxy holds the https and no proxy information ++ This is only for bottlerocket ++ properties: ++ httpsProxy: ++ description: HTTPS proxy ++ type: string ++ noProxy: ++ description: No proxy, list of ips that should not use ++ proxy ++ items: ++ type: string ++ type: array ++ type: object ++ registryMirror: ++ description: RegistryMirror holds the image registry mirror ++ information This is only for bottlerocket ++ properties: ++ caCert: ++ description: CACert defines the CA cert for the registry ++ mirror ++ type: string ++ endpoint: ++ description: Endpoint defines the registry mirror endpoint ++ to use for pulling images ++ type: string ++ type: object + type: object + mounts: + description: Mounts specifies a list of mount points to be setup. +@@ -2732,6 +2839,38 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketBootstrap: ++ description: BottlerocketBootstrap holds the image source ++ for kubeadm bootstrap container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object ++ bottlerocketControl: ++ description: BottlerocketControl holds the image source for ++ control container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object + certificatesDir: + description: 'CertificatesDir specifies where to store or + look for all required certificates. NB: if not provided, +@@ -2945,6 +3084,49 @@ spec: + "10.96.0.0/12" if that's unset. + type: string + type: object ++ pause: ++ description: Pause holds the image source for pause container ++ This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object ++ proxy: ++ description: Proxy holds the https and no proxy information ++ This is only for bottlerocket ++ properties: ++ httpsProxy: ++ description: HTTPS proxy ++ type: string ++ noProxy: ++ description: No proxy, list of ips that should not use ++ proxy ++ items: ++ type: string ++ type: array ++ type: object ++ registryMirror: ++ description: RegistryMirror holds the image registry mirror ++ information This is only for bottlerocket ++ properties: ++ caCert: ++ description: CACert defines the CA cert for the registry ++ mirror ++ type: string ++ endpoint: ++ description: Endpoint defines the registry mirror endpoint ++ to use for pulling images ++ type: string ++ type: object + scheduler: + description: Scheduler contains extra settings for the scheduler + control plane component +@@ -3360,49 +3542,6 @@ spec: + or by referencing a secret. + type: string + type: object +- pause: +- description: Pause holds the image source for pause container +- This is only for bottlerocket +- properties: +- imageRepository: +- description: ImageRepository sets the container registry +- to pull images from. if not set, the ImageRepository +- defined in ClusterConfiguration will be used instead. +- type: string +- imageTag: +- description: ImageTag allows to specify a tag for the +- image. In case this value is set, kubeadm does not change +- automatically the version of the above components during +- upgrades. +- type: string +- type: object +- proxy: +- description: Proxy holds the https and no proxy information +- This is only for bottlerocket +- properties: +- httpsProxy: +- description: HTTPS proxy +- type: string +- noProxy: +- description: No proxy, list of ips that should not use +- proxy +- items: +- type: string +- type: array +- type: object +- registryMirror: +- description: RegistryMirror holds the image registry mirror +- information This is only for bottlerocket +- properties: +- caCert: +- description: CACert defines the CA cert for the registry +- mirror +- type: string +- endpoint: +- description: Endpoint defines the registry mirror endpoint +- to use for pulling images +- type: string +- type: object + skipPhases: + description: SkipPhases is a list of phases to skip during + command execution. The list of phases can be obtained with +@@ -3422,6 +3561,38 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketBootstrap: ++ description: BottlerocketBootstrap holds the image source ++ for kubeadm bootstrap container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object ++ bottlerocketControl: ++ description: BottlerocketControl holds the image source for ++ control container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object + caCertPath: + description: 'CACertPath is the path to the SSL certificate + authority used to secure comunications between node and +@@ -3635,6 +3806,49 @@ spec: + or by referencing a secret. + type: string + type: object ++ pause: ++ description: Pause holds the image source for pause container ++ This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object ++ proxy: ++ description: Proxy holds the https and no proxy information ++ This is only for bottlerocket ++ properties: ++ httpsProxy: ++ description: HTTPS proxy ++ type: string ++ noProxy: ++ description: No proxy, list of ips that should not use ++ proxy ++ items: ++ type: string ++ type: array ++ type: object ++ registryMirror: ++ description: RegistryMirror holds the image registry mirror ++ information This is only for bottlerocket ++ properties: ++ caCert: ++ description: CACert defines the CA cert for the registry ++ mirror ++ type: string ++ endpoint: ++ description: Endpoint defines the registry mirror endpoint ++ to use for pulling images ++ type: string ++ type: object + skipPhases: + description: SkipPhases is a list of phases to skip during + command execution. The list of phases can be obtained with diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml index d4d5e0073..1d69bbe38 100644 --- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml @@ -1598,5 +2370,5 @@ index 8a29aaf52..56d79d966 100644 extraArgs: bar: baz -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0016-Change-format-for-storing-etcd-machine-address.patch b/projects/kubernetes-sigs/cluster-api/patches/0015-Change-format-for-storing-etcd-machine-address.patch similarity index 84% rename from projects/kubernetes-sigs/cluster-api/patches/0016-Change-format-for-storing-etcd-machine-address.patch rename to projects/kubernetes-sigs/cluster-api/patches/0015-Change-format-for-storing-etcd-machine-address.patch index 8b215c50dd..5cac6e8de7 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0016-Change-format-for-storing-etcd-machine-address.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0015-Change-format-for-storing-etcd-machine-address.patch @@ -1,7 +1,7 @@ -From 76f4d0880db6df346ad6e8c8f3528b63651ed00a Mon Sep 17 00:00:00 2001 +From 94f59d11a503717d73a5fe1b6afc13d1cbeddc9f Mon Sep 17 00:00:00 2001 From: Rajashree Mandaogane Date: Thu, 3 Mar 2022 15:01:35 -0800 -Subject: [PATCH 16/40] Change format for storing etcd machine address +Subject: [PATCH 15/40] Change format for storing etcd machine address Once the first etcd member is initialized, the machine controller has to update the secret with the address of the machine, so it can be used @@ -19,10 +19,10 @@ condition needs to be set based on the existence of this Secret. 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/internal/controllers/machine/machine_controller_phases.go b/internal/controllers/machine/machine_controller_phases.go -index 8eae496e0..9b251469e 100644 +index e22977cc0..41382bbaf 100644 --- a/internal/controllers/machine/machine_controller_phases.go +++ b/internal/controllers/machine/machine_controller_phases.go -@@ -362,7 +362,6 @@ func (r *Reconciler) reconcileInfrastructure(ctx context.Context, s *scope) (ctr +@@ -376,7 +376,6 @@ func (r *Reconciler) reconcileInfrastructure(ctx context.Context, s *scope) (ctr if machineIP == "" { return ctrl.Result{}, fmt.Errorf("error getting etcd init IP address: %v", err) } @@ -30,7 +30,7 @@ index 8eae496e0..9b251469e 100644 secret := &corev1.Secret{ ObjectMeta: metav1.ObjectMeta{ Name: etcdSecretName, -@@ -381,6 +380,7 @@ func (r *Reconciler) reconcileInfrastructure(ctx context.Context, s *scope) (ctr +@@ -395,6 +394,7 @@ func (r *Reconciler) reconcileInfrastructure(ctx context.Context, s *scope) (ctr }, Data: map[string][]byte{ "address": []byte(machineIP), @@ -39,5 +39,5 @@ index 8eae496e0..9b251469e 100644 Type: clusterv1.ClusterSecretType, } -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0017-Parse-provider-id-from-kubelet-extra-args.patch b/projects/kubernetes-sigs/cluster-api/patches/0016-Parse-provider-id-from-kubelet-extra-args.patch similarity index 93% rename from projects/kubernetes-sigs/cluster-api/patches/0017-Parse-provider-id-from-kubelet-extra-args.patch rename to projects/kubernetes-sigs/cluster-api/patches/0016-Parse-provider-id-from-kubelet-extra-args.patch index d8839936af..97b6c05cd6 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0017-Parse-provider-id-from-kubelet-extra-args.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0016-Parse-provider-id-from-kubelet-extra-args.patch @@ -1,7 +1,7 @@ -From 474294edd6b12c022497f1e6bb89d7ac21204f4f Mon Sep 17 00:00:00 2001 +From 995c5441e2293a643ea58ce3f0b16d0f61fbe6d1 Mon Sep 17 00:00:00 2001 From: Vignesh Goutham Ganesh Date: Wed, 8 Jun 2022 10:27:26 -0700 -Subject: [PATCH 17/40] Parse provider-id from kubelet extra args +Subject: [PATCH 16/40] Parse provider-id from kubelet extra args Signed-off-by: Vignesh Goutham Ganesh --- @@ -44,5 +44,5 @@ index 833f2d1c6..c9391fedb 100644 if config.BottlerocketControl.ImageRepository != "" && config.BottlerocketControl.ImageTag != "" { bottlerocketInput.ControlContainerSource = fmt.Sprintf("%s:%s", config.BottlerocketControl.ImageRepository, config.BottlerocketControl.ImageTag) -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0019-Add-feature-to-specifiy-additional-host-containers-i.patch b/projects/kubernetes-sigs/cluster-api/patches/0017-Add-feature-to-specifiy-additional-host-containers-i.patch similarity index 51% rename from projects/kubernetes-sigs/cluster-api/patches/0019-Add-feature-to-specifiy-additional-host-containers-i.patch rename to projects/kubernetes-sigs/cluster-api/patches/0017-Add-feature-to-specifiy-additional-host-containers-i.patch index 1c8db6d83f..6bed0f731e 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0019-Add-feature-to-specifiy-additional-host-containers-i.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0017-Add-feature-to-specifiy-additional-host-containers-i.patch @@ -1,7 +1,7 @@ -From 9cddc5c51ad3bec020f4872dd8c84612dc8116df Mon Sep 17 00:00:00 2001 +From 1a511864eb2ada9796e05a31155b0a156ac7b449 Mon Sep 17 00:00:00 2001 From: Victor Pineda Date: Tue, 21 Jun 2022 07:50:19 -0700 -Subject: [PATCH 19/40] Add feature to specifiy additional host containers in +Subject: [PATCH 17/40] Add feature to specifiy additional host containers in BR Host containers are a feature within BR that allows us to pull images @@ -19,21 +19,25 @@ SIM: https://i.amazon.com/P66557529 cr: https://code.amazon.com/reviews/CR-71408825 --- bootstrap/kubeadm/api/v1alpha4/conversion.go | 5 + - .../api/v1alpha4/zz_generated.conversion.go | 37 ++++-- - .../kubeadm/api/v1beta1/kubeadm_types.go | 25 +++++ - .../api/v1beta1/zz_generated.deepcopy.go | 26 +++++ - ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 84 ++++++++++++++ - ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 86 ++++++++++++++ - .../internal/bottlerocket/bootstrap.go | 44 +++----- - .../internal/bottlerocket/bottlerocket.go | 105 +++++++++++------- - .../controllers/kubeadmconfig_controller.go | 21 ++-- + .../kubeadm/api/v1alpha4/kubeadm_types.go | 25 ++ + .../api/v1alpha4/zz_generated.conversion.go | 77 +++++- + .../api/v1alpha4/zz_generated.deepcopy.go | 26 ++ + .../kubeadm/api/v1beta1/kubeadm_types.go | 25 ++ + .../api/v1beta1/zz_generated.deepcopy.go | 26 ++ + ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 252 +++++++++++++++++ + ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 258 ++++++++++++++++++ + .../internal/bottlerocket/bootstrap.go | 44 ++- + .../internal/bottlerocket/bottlerocket.go | 105 ++++--- + .../controllers/kubeadmconfig_controller.go | 21 +- + .../kubeadm/types/upstreamv1beta1/types.go | 25 ++ + .../upstreamv1beta1/zz_generated.deepcopy.go | 26 ++ .../types/upstreamv1beta2/conversion.go | 5 + - .../zz_generated.conversion.go | 17 ++- - .../types/upstreamv1beta3/conversion.go | 10 ++ - .../zz_generated.conversion.go | 32 ++---- - ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 86 ++++++++++++++ - ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 90 +++++++++++++++ - 15 files changed, 557 insertions(+), 116 deletions(-) + .../zz_generated.conversion.go | 17 +- + .../types/upstreamv1beta3/conversion.go | 10 + + .../zz_generated.conversion.go | 32 +-- + ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 258 ++++++++++++++++++ + ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 180 ++++++++++++ + 19 files changed, 1302 insertions(+), 115 deletions(-) diff --git a/bootstrap/kubeadm/api/v1alpha4/conversion.go b/bootstrap/kubeadm/api/v1alpha4/conversion.go index 576fceebd..5457cd58d 100644 @@ -51,23 +55,77 @@ index 576fceebd..5457cd58d 100644 func Convert_v1beta1_NodeRegistrationOptions_To_v1alpha4_NodeRegistrationOptions(in *bootstrapv1.NodeRegistrationOptions, out *NodeRegistrationOptions, s apiconversion.Scope) error { // NodeRegistrationOptions.ImagePullPolicy does not exit in // kubeadm v1alpha4 API. +diff --git a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +index 9027f336f..7f54b3b1d 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +@@ -151,6 +151,11 @@ type ClusterConfiguration struct { + // The cluster name + // +optional + ClusterName string `json:"clusterName,omitempty"` ++ ++ // BottlerocketHostContainers contains the information of any additional images ++ // that we will deploy as host containers in the CPIs ++ // +optional ++ BottlerocketHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` + } + + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. +@@ -449,6 +454,26 @@ type JoinConfiguration struct { + // If nil, no additional control plane instance will be deployed. + // +optional + ControlPlane *JoinControlPlane `json:"controlPlane,omitempty"` ++ ++ // BottlerocketCustomHostContainers contains the information of any additional images ++ // that we will deploy as host containers in the CPIs ++ // +optional ++ BottlerocketCustomHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` ++} ++ ++// BottlerocketHostContainer describes a host image for Bottlerocket ++type BottlerocketHostContainer struct { ++ // Name is the host container name that will be given to the container in BR's `apiserver` ++ // +kubebuilder:validation:Required ++ Name string `json:"name"` ++ // Superpowered indicates if the container will be superpowered ++ // +kubebuilder:validation:Required ++ Superpowered bool `json:"superpowered"` ++ // ImageMeta is the actual location of the container image ++ ImageMeta `json:"source"` ++ // UserData is the userdata that will be attached to the image. ++ // +optional ++ UserData string `json:"userData,omitempty"` + } + + // JoinControlPlane contains elements describing an additional control plane instance to be deployed on the joining node. diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -index 5c36c5ca4..fcea82a30 100644 +index 5c36c5ca4..02edbefcf 100644 --- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -@@ -115,11 +115,6 @@ func RegisterConversions(s *runtime.Scheme) error { +@@ -110,13 +110,18 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } +- if err := s.AddGeneratedConversionFunc((*ClusterConfiguration)(nil), (*v1beta1.ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { +- return Convert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(a.(*ClusterConfiguration), b.(*v1beta1.ClusterConfiguration), scope) ++ if err := s.AddGeneratedConversionFunc((*BottlerocketHostContainer)(nil), (*v1beta1.BottlerocketHostContainer)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_BottlerocketHostContainer_To_v1beta1_BottlerocketHostContainer(a.(*BottlerocketHostContainer), b.(*v1beta1.BottlerocketHostContainer), scope) }); err != nil { return err } - if err := s.AddGeneratedConversionFunc((*v1beta1.ClusterConfiguration)(nil), (*ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(a.(*v1beta1.ClusterConfiguration), b.(*ClusterConfiguration), scope) -- }); err != nil { -- return err -- } - if err := s.AddGeneratedConversionFunc((*ClusterStatus)(nil), (*v1beta1.ClusterStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1alpha4_ClusterStatus_To_v1beta1_ClusterStatus(a.(*ClusterStatus), b.(*v1beta1.ClusterStatus), scope) ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketHostContainer)(nil), (*BottlerocketHostContainer)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketHostContainer_To_v1alpha4_BottlerocketHostContainer(a.(*v1beta1.BottlerocketHostContainer), b.(*BottlerocketHostContainer), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*ClusterConfiguration)(nil), (*v1beta1.ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(a.(*ClusterConfiguration), b.(*v1beta1.ClusterConfiguration), scope) }); err != nil { -@@ -430,6 +425,11 @@ func RegisterConversions(s *runtime.Scheme) error { + return err + } +@@ -425,6 +430,11 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } @@ -76,14 +134,59 @@ index 5c36c5ca4..fcea82a30 100644 + }); err != nil { + return err + } - if err := s.AddConversionFunc((*v1beta1.InitConfiguration)(nil), (*InitConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1beta1_InitConfiguration_To_v1alpha4_InitConfiguration(a.(*v1beta1.InitConfiguration), b.(*InitConfiguration), scope) + if err := s.AddConversionFunc((*v1beta1.File)(nil), (*File)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_File_To_v1alpha4_File(a.(*v1beta1.File), b.(*File), scope) }); err != nil { -@@ -727,14 +727,10 @@ func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(i +@@ -639,6 +649,36 @@ func Convert_v1beta1_BottlerocketControl_To_v1alpha4_BottlerocketControl(in *v1b + return autoConvert_v1beta1_BottlerocketControl_To_v1alpha4_BottlerocketControl(in, out, s) + } + ++func autoConvert_v1alpha4_BottlerocketHostContainer_To_v1beta1_BottlerocketHostContainer(in *BottlerocketHostContainer, out *v1beta1.BottlerocketHostContainer, s conversion.Scope) error { ++ out.Name = in.Name ++ out.Superpowered = in.Superpowered ++ if err := Convert_v1alpha4_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ out.UserData = in.UserData ++ return nil ++} ++ ++// Convert_v1alpha4_BottlerocketHostContainer_To_v1beta1_BottlerocketHostContainer is an autogenerated conversion function. ++func Convert_v1alpha4_BottlerocketHostContainer_To_v1beta1_BottlerocketHostContainer(in *BottlerocketHostContainer, out *v1beta1.BottlerocketHostContainer, s conversion.Scope) error { ++ return autoConvert_v1alpha4_BottlerocketHostContainer_To_v1beta1_BottlerocketHostContainer(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketHostContainer_To_v1alpha4_BottlerocketHostContainer(in *v1beta1.BottlerocketHostContainer, out *BottlerocketHostContainer, s conversion.Scope) error { ++ out.Name = in.Name ++ out.Superpowered = in.Superpowered ++ if err := Convert_v1beta1_ImageMeta_To_v1alpha4_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ out.UserData = in.UserData ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketHostContainer_To_v1alpha4_BottlerocketHostContainer is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketHostContainer_To_v1alpha4_BottlerocketHostContainer(in *v1beta1.BottlerocketHostContainer, out *BottlerocketHostContainer, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketHostContainer_To_v1alpha4_BottlerocketHostContainer(in, out, s) ++} ++ + func autoConvert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *ClusterConfiguration, out *v1beta1.ClusterConfiguration, s conversion.Scope) error { + if err := Convert_v1alpha4_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { + return err +@@ -679,6 +719,7 @@ func autoConvert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(i out.ImageRepository = in.ImageRepository out.FeatureGates = *(*map[string]bool)(unsafe.Pointer(&in.FeatureGates)) out.ClusterName = in.ClusterName -+ // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type ++ out.BottlerocketHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) + return nil + } + +@@ -727,14 +768,10 @@ func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(i + out.ImageRepository = in.ImageRepository + out.FeatureGates = *(*map[string]bool)(unsafe.Pointer(&in.FeatureGates)) + out.ClusterName = in.ClusterName ++ out.BottlerocketHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) return nil } @@ -95,15 +198,23 @@ index 5c36c5ca4..fcea82a30 100644 func autoConvert_v1alpha4_ClusterStatus_To_v1beta1_ClusterStatus(in *ClusterStatus, out *v1beta1.ClusterStatus, s conversion.Scope) error { out.APIEndpoints = *(*map[string]v1beta1.APIEndpoint)(unsafe.Pointer(&in.APIEndpoints)) return nil -@@ -1136,6 +1132,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1b +@@ -1102,6 +1139,7 @@ func autoConvert_v1alpha4_JoinConfiguration_To_v1beta1_JoinConfiguration(in *Joi + return err + } + out.ControlPlane = (*v1beta1.JoinControlPlane)(unsafe.Pointer(in.ControlPlane)) ++ out.BottlerocketCustomHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) + return nil + } + +@@ -1136,6 +1174,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1b out.ControlPlane = (*JoinControlPlane)(unsafe.Pointer(in.ControlPlane)) // WARNING: in.SkipPhases requires manual conversion: does not exist in peer-type // WARNING: in.Patches requires manual conversion: does not exist in peer-type -+ // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type ++ out.BottlerocketCustomHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) return nil } -@@ -1238,7 +1235,15 @@ func Convert_v1beta1_KubeadmConfigList_To_v1alpha4_KubeadmConfigList(in *v1beta1 +@@ -1238,7 +1277,15 @@ func Convert_v1beta1_KubeadmConfigList_To_v1alpha4_KubeadmConfigList(in *v1beta1 } func autoConvert_v1alpha4_KubeadmConfigSpec_To_v1beta1_KubeadmConfigSpec(in *KubeadmConfigSpec, out *v1beta1.KubeadmConfigSpec, s conversion.Scope) error { @@ -120,7 +231,7 @@ index 5c36c5ca4..fcea82a30 100644 if in.InitConfiguration != nil { in, out := &in.InitConfiguration, &out.InitConfiguration *out = new(v1beta1.InitConfiguration) -@@ -1296,7 +1301,15 @@ func Convert_v1alpha4_KubeadmConfigSpec_To_v1beta1_KubeadmConfigSpec(in *Kubeadm +@@ -1296,7 +1343,15 @@ func Convert_v1alpha4_KubeadmConfigSpec_To_v1beta1_KubeadmConfigSpec(in *Kubeadm } func autoConvert_v1beta1_KubeadmConfigSpec_To_v1alpha4_KubeadmConfigSpec(in *v1beta1.KubeadmConfigSpec, out *KubeadmConfigSpec, s conversion.Scope) error { @@ -137,6 +248,57 @@ index 5c36c5ca4..fcea82a30 100644 if in.InitConfiguration != nil { in, out := &in.InitConfiguration, &out.InitConfiguration *out = new(InitConfiguration) +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +index 5bf4e0d97..f8a680800 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +@@ -174,6 +174,22 @@ func (in *BottlerocketControl) DeepCopy() *BottlerocketControl { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketHostContainer) DeepCopyInto(out *BottlerocketHostContainer) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketHostContainer. ++func (in *BottlerocketHostContainer) DeepCopy() *BottlerocketHostContainer { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketHostContainer) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = *in +@@ -196,6 +212,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + (*out)[key] = val + } + } ++ if in.BottlerocketHostContainers != nil { ++ in, out := &in.BottlerocketHostContainers, &out.BottlerocketHostContainers ++ *out = make([]BottlerocketHostContainer, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. +@@ -559,6 +580,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = new(JoinControlPlane) + **out = **in + } ++ if in.BottlerocketCustomHostContainers != nil { ++ in, out := &in.BottlerocketCustomHostContainers, &out.BottlerocketCustomHostContainers ++ *out = make([]BottlerocketHostContainer, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go index 8c9dcac00..44ffa00f3 100644 --- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go @@ -232,10 +394,10 @@ index 80d9362bb..8da1eb4c5 100644 // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -index e0ca0a0ca..649b9c0bc 100644 +index f0e8338be..b2b01cb68 100644 --- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -@@ -1267,6 +1267,48 @@ spec: +@@ -133,6 +133,48 @@ spec: the version of the above components during upgrades. type: string type: object @@ -284,7 +446,7 @@ index e0ca0a0ca..649b9c0bc 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, this will -@@ -1960,6 +2002,48 @@ spec: +@@ -761,6 +803,48 @@ spec: the version of the above components during upgrades. type: string type: object @@ -333,144 +495,540 @@ index e0ca0a0ca..649b9c0bc 100644 caCertPath: description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node and control-plane. -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -index 606155b09..21173d07f 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -@@ -1302,6 +1302,49 @@ spec: - components during upgrades. - type: string - type: object -+ bottlerocketCustomHostContainers: -+ description: BottlerocketHostContainers contains the information -+ of any additional images that we will deploy as host -+ containers in the CPIs -+ items: -+ description: BottlerocketHostContainer describes a host -+ image for Bottlerocket -+ properties: -+ name: -+ description: Name is the host container name that -+ will be given to the container in BR's `apiserver` -+ type: string -+ source: -+ description: ImageMeta is the actual location of -+ the container image -+ properties: -+ imageRepository: -+ description: ImageRepository sets the container -+ registry to pull images from. if not set, -+ the ImageRepository defined in ClusterConfiguration -+ will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag -+ for the image. In case this value is set, -+ kubeadm does not change automatically the -+ version of the above components during upgrades. -+ type: string -+ type: object -+ superpowered: -+ description: Superpowered indicates if the container -+ will be superpowered -+ type: boolean -+ userData: -+ description: UserData is the userdata that will -+ be attached to the image. -+ type: string -+ required: -+ - name -+ - source -+ - superpowered -+ type: object -+ type: array - certificatesDir: - description: 'CertificatesDir specifies where to store - or look for all required certificates. NB: if not provided, -@@ -2044,6 +2087,49 @@ spec: - components during upgrades. - type: string - type: object -+ bottlerocketCustomHostContainers: -+ description: BottlerocketCustomHostContainers contains -+ the information of any additional images that we will -+ deploy as host containers in the CPIs -+ items: -+ description: BottlerocketHostContainer describes a host -+ image for Bottlerocket -+ properties: -+ name: -+ description: Name is the host container name that -+ will be given to the container in BR's `apiserver` -+ type: string -+ source: -+ description: ImageMeta is the actual location of -+ the container image -+ properties: -+ imageRepository: -+ description: ImageRepository sets the container -+ registry to pull images from. if not set, -+ the ImageRepository defined in ClusterConfiguration -+ will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag -+ for the image. In case this value is set, -+ kubeadm does not change automatically the -+ version of the above components during upgrades. -+ type: string -+ type: object -+ superpowered: -+ description: Superpowered indicates if the container -+ will be superpowered -+ type: boolean -+ userData: -+ description: UserData is the userdata that will -+ be attached to the image. -+ type: string -+ required: -+ - name -+ - source -+ - superpowered -+ type: object -+ type: array - caCertPath: - description: 'CACertPath is the path to the SSL certificate - authority used to secure comunications between node -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -index efdb51fef..bc5094eb1 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -@@ -3,12 +3,6 @@ - package bottlerocket - - const ( -- adminContainerInitTemplate = `{{ define "adminContainerInitSettings" -}} --[settings.host-containers.admin] --enabled = true --user-data = "{{.AdminContainerUserData}}" --{{- end -}} --` - kubernetesInitTemplate = `{{ define "kubernetesInitSettings" -}} - [settings.kubernetes] - cluster-domain = "cluster.local" -@@ -22,14 +16,26 @@ provider-id = "{{.ProviderId}}" - {{- end -}} - ` - -- bootstrapHostContainerTemplate = `{{define "bootstrapHostContainerSettings" -}} --[settings.host-containers.kubeadm-bootstrap] -+ hostContainerTemplate = `{{define "hostContainerSettings" -}} -+[settings.host-containers.{{.Name}}] - enabled = true --superpowered = true --source = "{{.BootstrapContainerSource}}" --user-data = "{{.BootstrapContainerUserData}}" -+superpowered = {{.Superpowered}} -+{{- if (ne (imageUrl .ImageMeta) "")}} -+source = "{{imageUrl .ImageMeta}}" -+{{- end -}} -+{{- if (ne .UserData "")}} +@@ -1268,6 +1352,48 @@ spec: + the version of the above components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketHostContainers contains the information ++ of any additional images that we will deploy as host containers ++ in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host image ++ for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that will be ++ given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of the container ++ image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not ++ change automatically the version of the above components ++ during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container will ++ be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will be attached ++ to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store or look + for all required certificates. NB: if not provided, this will +@@ -1892,6 +2018,48 @@ spec: + the version of the above components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketCustomHostContainers contains the information ++ of any additional images that we will deploy as host containers ++ in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host image ++ for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that will be ++ given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of the container ++ image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not ++ change automatically the version of the above components ++ during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container will ++ be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will be attached ++ to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + caCertPath: + description: 'CACertPath is the path to the SSL certificate authority + used to secure comunications between node and control-plane. +@@ -2397,6 +2565,48 @@ spec: + the version of the above components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketHostContainers contains the information ++ of any additional images that we will deploy as host containers ++ in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host image ++ for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that will be ++ given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of the container ++ image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not ++ change automatically the version of the above components ++ during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container will ++ be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will be attached ++ to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store or look + for all required certificates. NB: if not provided, this will +@@ -3090,6 +3300,48 @@ spec: + the version of the above components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketCustomHostContainers contains the information ++ of any additional images that we will deploy as host containers ++ in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host image ++ for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that will be ++ given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of the container ++ image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not ++ change automatically the version of the above components ++ during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container will ++ be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will be attached ++ to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + caCertPath: + description: 'CACertPath is the path to the SSL certificate authority + used to secure comunications between node and control-plane. +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +index 6586d0dbf..311b5d79f 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +@@ -143,6 +143,49 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketHostContainers contains the information ++ of any additional images that we will deploy as host ++ containers in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host ++ image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that ++ will be given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of ++ the container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, ++ kubeadm does not change automatically the ++ version of the above components during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will ++ be attached to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store + or look for all required certificates. NB: if not provided, +@@ -810,6 +853,49 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketCustomHostContainers contains ++ the information of any additional images that we will ++ deploy as host containers in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host ++ image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that ++ will be given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of ++ the container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, ++ kubeadm does not change automatically the ++ version of the above components during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will ++ be attached to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + caCertPath: + description: 'CACertPath is the path to the SSL certificate + authority used to secure comunications between node +@@ -1276,6 +1362,49 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketHostContainers contains the information ++ of any additional images that we will deploy as host ++ containers in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host ++ image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that ++ will be given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of ++ the container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, ++ kubeadm does not change automatically the ++ version of the above components during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will ++ be attached to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store + or look for all required certificates. NB: if not provided, +@@ -1941,6 +2070,49 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketCustomHostContainers contains ++ the information of any additional images that we will ++ deploy as host containers in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host ++ image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that ++ will be given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of ++ the container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, ++ kubeadm does not change automatically the ++ version of the above components during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will ++ be attached to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + caCertPath: + description: 'CACertPath is the path to the SSL certificate + authority used to secure comunications between node +@@ -2430,6 +2602,49 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketHostContainers contains the information ++ of any additional images that we will deploy as host ++ containers in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host ++ image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that ++ will be given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of ++ the container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, ++ kubeadm does not change automatically the ++ version of the above components during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will ++ be attached to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store + or look for all required certificates. NB: if not provided, +@@ -3172,6 +3387,49 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketCustomHostContainers contains ++ the information of any additional images that we will ++ deploy as host containers in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host ++ image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that ++ will be given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of ++ the container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, ++ kubeadm does not change automatically the ++ version of the above components during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will ++ be attached to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + caCertPath: + description: 'CACertPath is the path to the SSL certificate + authority used to secure comunications between node +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +index efdb51fef..bc5094eb1 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +@@ -3,12 +3,6 @@ + package bottlerocket + + const ( +- adminContainerInitTemplate = `{{ define "adminContainerInitSettings" -}} +-[settings.host-containers.admin] +-enabled = true +-user-data = "{{.AdminContainerUserData}}" +-{{- end -}} +-` + kubernetesInitTemplate = `{{ define "kubernetesInitSettings" -}} + [settings.kubernetes] + cluster-domain = "cluster.local" +@@ -22,14 +16,26 @@ provider-id = "{{.ProviderId}}" + {{- end -}} + ` + +- bootstrapHostContainerTemplate = `{{define "bootstrapHostContainerSettings" -}} +-[settings.host-containers.kubeadm-bootstrap] ++ hostContainerTemplate = `{{define "hostContainerSettings" -}} ++[settings.host-containers.{{.Name}}] + enabled = true +-superpowered = true +-source = "{{.BootstrapContainerSource}}" +-user-data = "{{.BootstrapContainerUserData}}" ++superpowered = {{.Superpowered}} ++{{- if (ne (imageUrl .ImageMeta) "")}} ++source = "{{imageUrl .ImageMeta}}" ++{{- end -}} ++{{- if (ne .UserData "")}} +user-data = "{{.UserData}}" +{{- end -}} +{{- end -}} @@ -706,6 +1264,100 @@ index fd96264ea..8eb1d6c02 100644 } if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/types.go b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +index 6ac8e40d4..2fb4e6e19 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/types.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +@@ -149,6 +149,11 @@ type ClusterConfiguration struct { + // The cluster name + // +optional + ClusterName string `json:"clusterName,omitempty"` ++ ++ // BottlerocketHostContainers contains the information of any additional images ++ // that we will deploy as host containers in the CPIs ++ // +optional ++ BottlerocketHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` + } + + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. +@@ -438,6 +443,26 @@ type JoinConfiguration struct { + // If nil, no additional control plane instance will be deployed. + // +optional + ControlPlane *JoinControlPlane `json:"controlPlane,omitempty"` ++ ++ // BottlerocketCustomHostContainers contains the information of any additional images ++ // that we will deploy as host containers in the CPIs ++ // +optional ++ BottlerocketCustomHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` ++} ++ ++// BottlerocketHostContainer describes a host image for Bottlerocket ++type BottlerocketHostContainer struct { ++ // Name is the host container name that will be given to the container in BR's `apiserver` ++ // +kubebuilder:validation:Required ++ Name string `json:"name"` ++ // Superpowered indicates if the container will be superpowered ++ // +kubebuilder:validation:Required ++ Superpowered bool `json:"superpowered"` ++ // ImageMeta is the actual location of the container image ++ ImageMeta `json:"source"` ++ // UserData is the userdata that will be attached to the image. ++ // +optional ++ UserData string `json:"userData,omitempty"` + } + + // JoinControlPlane contains elements describing an additional control plane instance to be deployed on the joining node. +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +index a48491019..03d4640e6 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +@@ -173,6 +173,22 @@ func (in *BottlerocketControl) DeepCopy() *BottlerocketControl { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketHostContainer) DeepCopyInto(out *BottlerocketHostContainer) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketHostContainer. ++func (in *BottlerocketHostContainer) DeepCopy() *BottlerocketHostContainer { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketHostContainer) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = *in +@@ -195,6 +211,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + (*out)[key] = val + } + } ++ if in.BottlerocketHostContainers != nil { ++ in, out := &in.BottlerocketHostContainers, &out.BottlerocketHostContainers ++ *out = make([]BottlerocketHostContainer, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. +@@ -458,6 +479,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = new(JoinControlPlane) + **out = **in + } ++ if in.BottlerocketCustomHostContainers != nil { ++ in, out := &in.BottlerocketCustomHostContainers, &out.BottlerocketCustomHostContainers ++ *out = make([]BottlerocketHostContainer, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/conversion.go index fc95ca21d..20f52cae5 100644 --- a/bootstrap/kubeadm/types/upstreamv1beta2/conversion.go @@ -870,10 +1522,210 @@ index 197c2ef74..d290e4d94 100644 if err := Convert_upstreamv1beta3_APIEndpoint_To_v1beta1_APIEndpoint(&in.LocalAPIEndpoint, &out.LocalAPIEndpoint, s); err != nil { return err diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -index 6aba94af6..b3d5958dc 100644 +index b207309b9..77ca12b3b 100644 --- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -@@ -1547,6 +1547,49 @@ spec: +@@ -210,6 +210,49 @@ spec: + upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketHostContainers contains the information ++ of any additional images that we will deploy as host containers ++ in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host ++ image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that will ++ be given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of the ++ container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm ++ does not change automatically the version of the ++ above components during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will be attached ++ to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store or + look for all required certificates. NB: if not provided, +@@ -862,6 +905,49 @@ spec: + upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketCustomHostContainers contains the ++ information of any additional images that we will deploy ++ as host containers in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host ++ image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that will ++ be given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of the ++ container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm ++ does not change automatically the version of the ++ above components during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will be attached ++ to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + caCertPath: + description: 'CACertPath is the path to the SSL certificate + authority used to secure comunications between node and +@@ -1500,6 +1586,49 @@ spec: + upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketHostContainers contains the information ++ of any additional images that we will deploy as host containers ++ in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host ++ image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that will ++ be given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of the ++ container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm ++ does not change automatically the version of the ++ above components during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will be attached ++ to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store or + look for all required certificates. NB: if not provided, +@@ -2149,6 +2278,49 @@ spec: + upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketCustomHostContainers contains the ++ information of any additional images that we will deploy ++ as host containers in the CPIs ++ items: ++ description: BottlerocketHostContainer describes a host ++ image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name that will ++ be given to the container in BR's `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location of the ++ container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm ++ does not change automatically the version of the ++ above components during upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will be attached ++ to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + caCertPath: + description: 'CACertPath is the path to the SSL certificate + authority used to secure comunications between node and +@@ -2871,6 +3043,49 @@ spec: upgrades. type: string type: object @@ -923,7 +1775,7 @@ index 6aba94af6..b3d5958dc 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not provided, -@@ -2269,6 +2312,49 @@ spec: +@@ -3593,6 +3808,49 @@ spec: upgrades. type: string type: object @@ -974,10 +1826,114 @@ index 6aba94af6..b3d5958dc 100644 description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node and diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -index 1d69bbe38..a9d34477b 100644 +index 1d69bbe38..2f9941558 100644 --- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -@@ -1503,6 +1503,51 @@ spec: +@@ -160,6 +160,51 @@ spec: + the above components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketHostContainers contains the ++ information of any additional images that we will ++ deploy as host containers in the CPIs ++ items: ++ description: BottlerocketHostContainer describes ++ a host image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name ++ that will be given to the container in BR's ++ `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location ++ of the container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify ++ a tag for the image. In case this value ++ is set, kubeadm does not change automatically ++ the version of the above components during ++ upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will ++ be attached to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store + or look for all required certificates. NB: if not +@@ -853,6 +898,51 @@ spec: + the above components during upgrades. + type: string + type: object ++ bottlerocketCustomHostContainers: ++ description: BottlerocketCustomHostContainers contains ++ the information of any additional images that we ++ will deploy as host containers in the CPIs ++ items: ++ description: BottlerocketHostContainer describes ++ a host image for Bottlerocket ++ properties: ++ name: ++ description: Name is the host container name ++ that will be given to the container in BR's ++ `apiserver` ++ type: string ++ source: ++ description: ImageMeta is the actual location ++ of the container image ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify ++ a tag for the image. In case this value ++ is set, kubeadm does not change automatically ++ the version of the above components during ++ upgrades. ++ type: string ++ type: object ++ superpowered: ++ description: Superpowered indicates if the container ++ will be superpowered ++ type: boolean ++ userData: ++ description: UserData is the userdata that will ++ be attached to the image. ++ type: string ++ required: ++ - name ++ - source ++ - superpowered ++ type: object ++ type: array + caCertPath: + description: 'CACertPath is the path to the SSL certificate + authority used to secure comunications between node +@@ -1503,6 +1593,51 @@ spec: the above components during upgrades. type: string type: object @@ -1029,7 +1985,7 @@ index 1d69bbe38..a9d34477b 100644 certificatesDir: description: 'CertificatesDir specifies where to store or look for all required certificates. NB: if not -@@ -2275,6 +2320,51 @@ spec: +@@ -2275,6 +2410,51 @@ spec: the above components during upgrades. type: string type: object @@ -1082,5 +2038,5 @@ index 1d69bbe38..a9d34477b 100644 description: 'CACertPath is the path to the SSL certificate authority used to secure comunications between node -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0018-Add-bottlerocket-control-image-on-nodes-joining-a-ne.patch b/projects/kubernetes-sigs/cluster-api/patches/0018-Add-bottlerocket-control-image-on-nodes-joining-a-ne.patch deleted file mode 100644 index 23cdbca6f3..0000000000 --- a/projects/kubernetes-sigs/cluster-api/patches/0018-Add-bottlerocket-control-image-on-nodes-joining-a-ne.patch +++ /dev/null @@ -1,25 +0,0 @@ -From 1c92f4172bfdd4bd8c6d86cacd668d31781485c5 Mon Sep 17 00:00:00 2001 -From: Victor Pineda -Date: Sun, 19 Jun 2022 10:39:50 -0700 -Subject: [PATCH 18/40] Add bottlerocket control image on nodes joining a new - cluster - ---- - .../kubeadm/internal/controllers/kubeadmconfig_controller.go | 1 + - 1 file changed, 1 insertion(+) - -diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -index d5dc72b76..fd96264ea 100644 ---- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -+++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -@@ -807,6 +807,7 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S - bottlerocketConfig := &bottlerocket.BottlerocketConfig{ - Pause: scope.Config.Spec.JoinConfiguration.Pause, - BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, -+ BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, - } - if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { - bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy --- -2.39.3 (Apple Git-145) - diff --git a/projects/kubernetes-sigs/cluster-api/patches/0018-Add-bottlerocket-custom-bootstrap-containers-config-.patch b/projects/kubernetes-sigs/cluster-api/patches/0018-Add-bottlerocket-custom-bootstrap-containers-config-.patch new file mode 100644 index 0000000000..7296b3b584 --- /dev/null +++ b/projects/kubernetes-sigs/cluster-api/patches/0018-Add-bottlerocket-custom-bootstrap-containers-config-.patch @@ -0,0 +1,1946 @@ +From b0a1e39aa3ab58e0023cab81d0bd940b1569cf5f Mon Sep 17 00:00:00 2001 +From: Jiayi Wang +Date: Mon, 21 Nov 2022 17:31:22 -0500 +Subject: [PATCH 18/40] Add bottlerocket custom bootstrap containers config + option + +--- + .../kubeadm/api/v1alpha4/kubeadm_types.go | 33 ++ + .../api/v1alpha4/zz_generated.conversion.go | 46 +++ + .../api/v1alpha4/zz_generated.deepcopy.go | 26 ++ + .../kubeadm/api/v1beta1/kubeadm_types.go | 36 ++- + .../api/v1beta1/zz_generated.deepcopy.go | 26 ++ + ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 252 ++++++++++++++++ + ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 282 ++++++++++++++++++ + .../internal/bottlerocket/bootstrap.go | 24 ++ + .../internal/bottlerocket/bootstrap_test.go | 99 ++++++ + .../internal/bottlerocket/bottlerocket.go | 27 +- + .../controllers/kubeadmconfig_controller.go | 27 +- + .../kubeadm/types/upstreamv1beta1/types.go | 33 ++ + .../upstreamv1beta1/zz_generated.deepcopy.go | 26 ++ + .../zz_generated.conversion.go | 2 + + .../zz_generated.conversion.go | 2 + + ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 276 +++++++++++++++++ + ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 200 +++++++++++++ + 17 files changed, 1394 insertions(+), 23 deletions(-) + create mode 100644 bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go + +diff --git a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +index 7f54b3b1d..592c257b8 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +@@ -156,6 +156,11 @@ type ClusterConfiguration struct { + // that we will deploy as host containers in the CPIs + // +optional + BottlerocketHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` ++ ++ // BottlerocketCustomBootstrapContainers adds additional bootstrap containers for Bottlerocket. ++ // This is only for bottlerocket. ++ // +optional ++ BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` + } + + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. +@@ -459,6 +464,11 @@ type JoinConfiguration struct { + // that we will deploy as host containers in the CPIs + // +optional + BottlerocketCustomHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` ++ ++ // BottlerocketCustomBootstrapContainers adds additional bootstrap containers for Bottlerocket. ++ // This is only for bottlerocket. ++ // +optional ++ BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` + } + + // BottlerocketHostContainer describes a host image for Bottlerocket +@@ -476,6 +486,29 @@ type BottlerocketHostContainer struct { + UserData string `json:"userData,omitempty"` + } + ++// BottlerocketBootstrapContainer holds the bootstrap container setting for Bottlerocket ++type BottlerocketBootstrapContainer struct { ++ // Name is the bootstrap container name that will be given to the container in BR's `apiserver`. ++ Name string `json:"name"` ++ ++ // ImageMeta is the actual image used for Bottlerocket bootstrap. ++ ImageMeta `json:",inline"` ++ ++ // Essential decides whether or not the container should fail the boot process. ++ // Bootstrap containers configured with essential = true will stop the boot process if they exit code is a non-zero value. ++ // Default is false. ++ // +optional ++ Essential bool `json:"essential"` ++ ++ // Mode represents the bootstrap container mode. ++ // +kubebuilder:validation:Enum=always;off;once ++ Mode string `json:"mode"` ++ ++ // UserData is the base64-encoded userdata. ++ // +optional ++ UserData string `json:"userData,omitempty"` ++} ++ + // JoinControlPlane contains elements describing an additional control plane instance to be deployed on the joining node. + type JoinControlPlane struct { + // LocalAPIEndpoint represents the endpoint of the API server instance to be deployed on this node. +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +index 02edbefcf..2b70d0c11 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +@@ -100,6 +100,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrapContainer)(nil), (*v1beta1.BottlerocketBootstrapContainer)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_BottlerocketBootstrapContainer_To_v1beta1_BottlerocketBootstrapContainer(a.(*BottlerocketBootstrapContainer), b.(*v1beta1.BottlerocketBootstrapContainer), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketBootstrapContainer)(nil), (*BottlerocketBootstrapContainer)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketBootstrapContainer_To_v1alpha4_BottlerocketBootstrapContainer(a.(*v1beta1.BottlerocketBootstrapContainer), b.(*BottlerocketBootstrapContainer), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*BottlerocketControl)(nil), (*v1beta1.BottlerocketControl)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1alpha4_BottlerocketControl_To_v1beta1_BottlerocketControl(a.(*BottlerocketControl), b.(*v1beta1.BottlerocketControl), scope) + }); err != nil { +@@ -625,6 +635,38 @@ func Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(in + return autoConvert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(in, out, s) + } + ++func autoConvert_v1alpha4_BottlerocketBootstrapContainer_To_v1beta1_BottlerocketBootstrapContainer(in *BottlerocketBootstrapContainer, out *v1beta1.BottlerocketBootstrapContainer, s conversion.Scope) error { ++ out.Name = in.Name ++ if err := Convert_v1alpha4_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ out.Essential = in.Essential ++ out.Mode = in.Mode ++ out.UserData = in.UserData ++ return nil ++} ++ ++// Convert_v1alpha4_BottlerocketBootstrapContainer_To_v1beta1_BottlerocketBootstrapContainer is an autogenerated conversion function. ++func Convert_v1alpha4_BottlerocketBootstrapContainer_To_v1beta1_BottlerocketBootstrapContainer(in *BottlerocketBootstrapContainer, out *v1beta1.BottlerocketBootstrapContainer, s conversion.Scope) error { ++ return autoConvert_v1alpha4_BottlerocketBootstrapContainer_To_v1beta1_BottlerocketBootstrapContainer(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketBootstrapContainer_To_v1alpha4_BottlerocketBootstrapContainer(in *v1beta1.BottlerocketBootstrapContainer, out *BottlerocketBootstrapContainer, s conversion.Scope) error { ++ out.Name = in.Name ++ if err := Convert_v1beta1_ImageMeta_To_v1alpha4_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ out.Essential = in.Essential ++ out.Mode = in.Mode ++ out.UserData = in.UserData ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketBootstrapContainer_To_v1alpha4_BottlerocketBootstrapContainer is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketBootstrapContainer_To_v1alpha4_BottlerocketBootstrapContainer(in *v1beta1.BottlerocketBootstrapContainer, out *BottlerocketBootstrapContainer, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketBootstrapContainer_To_v1alpha4_BottlerocketBootstrapContainer(in, out, s) ++} ++ + func autoConvert_v1alpha4_BottlerocketControl_To_v1beta1_BottlerocketControl(in *BottlerocketControl, out *v1beta1.BottlerocketControl, s conversion.Scope) error { + if err := Convert_v1alpha4_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { + return err +@@ -720,6 +762,7 @@ func autoConvert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(i + out.FeatureGates = *(*map[string]bool)(unsafe.Pointer(&in.FeatureGates)) + out.ClusterName = in.ClusterName + out.BottlerocketHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) ++ out.BottlerocketCustomBootstrapContainers = *(*[]v1beta1.BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + return nil + } + +@@ -769,6 +812,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(i + out.FeatureGates = *(*map[string]bool)(unsafe.Pointer(&in.FeatureGates)) + out.ClusterName = in.ClusterName + out.BottlerocketHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) ++ out.BottlerocketCustomBootstrapContainers = *(*[]BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + return nil + } + +@@ -1140,6 +1184,7 @@ func autoConvert_v1alpha4_JoinConfiguration_To_v1beta1_JoinConfiguration(in *Joi + } + out.ControlPlane = (*v1beta1.JoinControlPlane)(unsafe.Pointer(in.ControlPlane)) + out.BottlerocketCustomHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) ++ out.BottlerocketCustomBootstrapContainers = *(*[]v1beta1.BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + return nil + } + +@@ -1175,6 +1220,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1b + // WARNING: in.SkipPhases requires manual conversion: does not exist in peer-type + // WARNING: in.Patches requires manual conversion: does not exist in peer-type + out.BottlerocketCustomHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) ++ out.BottlerocketCustomBootstrapContainers = *(*[]BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + return nil + } + +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +index f8a680800..c7f644c8f 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +@@ -158,6 +158,22 @@ func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketBootstrapContainer) DeepCopyInto(out *BottlerocketBootstrapContainer) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootstrapContainer. ++func (in *BottlerocketBootstrapContainer) DeepCopy() *BottlerocketBootstrapContainer { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketBootstrapContainer) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketControl) DeepCopyInto(out *BottlerocketControl) { + *out = *in +@@ -217,6 +233,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = make([]BottlerocketHostContainer, len(*in)) + copy(*out, *in) + } ++ if in.BottlerocketCustomBootstrapContainers != nil { ++ in, out := &in.BottlerocketCustomBootstrapContainers, &out.BottlerocketCustomBootstrapContainers ++ *out = make([]BottlerocketBootstrapContainer, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. +@@ -585,6 +606,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = make([]BottlerocketHostContainer, len(*in)) + copy(*out, *in) + } ++ if in.BottlerocketCustomBootstrapContainers != nil { ++ in, out := &in.BottlerocketCustomBootstrapContainers, &out.BottlerocketCustomBootstrapContainers ++ *out = make([]BottlerocketBootstrapContainer, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. +diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +index 44ffa00f3..48e5f4b8e 100644 +--- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +@@ -175,6 +175,11 @@ type ClusterConfiguration struct { + // that we will deploy as host containers in the CPIs + // +optional + BottlerocketHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` ++ ++ // BottlerocketCustomBootstrapContainers adds additional bootstrap containers for Bottlerocket. ++ // This is only for bottlerocket. ++ // +optional ++ BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` + } + + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. +@@ -261,7 +266,7 @@ type ImageMeta struct { + // +optional + ImageTag string `json:"imageTag,omitempty"` + +- //TODO: evaluate if we need also a ImageName based on user feedbacks ++ // TODO: evaluate if we need also a ImageName based on user feedbacks + } + + // +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object +@@ -424,7 +429,6 @@ type BootstrapToken struct { + + // Etcd contains elements describing Etcd configuration. + type Etcd struct { +- + // Local provides configuration knobs for configuring the local etcd instance + // Local and External are mutually exclusive + // +optional +@@ -547,6 +551,11 @@ type JoinConfiguration struct { + // that we will deploy as host containers in the CPIs + // +optional + BottlerocketCustomHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` ++ ++ // BottlerocketCustomBootstrapContainers adds additional bootstrap containers for Bottlerocket. ++ // This is only for bottlerocket. ++ // +optional ++ BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` + } + + // BottlerocketHostContainer describes a host image for Bottlerocket +@@ -564,6 +573,29 @@ type BottlerocketHostContainer struct { + UserData string `json:"userData,omitempty"` + } + ++// BottlerocketBootstrapContainer holds the bootstrap container setting for Bottlerocket ++type BottlerocketBootstrapContainer struct { ++ // Name is the bootstrap container name that will be given to the container in BR's `apiserver`. ++ Name string `json:"name"` ++ ++ // ImageMeta is the actual image used for Bottlerocket bootstrap. ++ ImageMeta `json:",inline"` ++ ++ // Essential decides whether or not the container should fail the boot process. ++ // Bootstrap containers configured with essential = true will stop the boot process if they exit code is a non-zero value. ++ // Default is false. ++ // +optional ++ Essential bool `json:"essential"` ++ ++ // Mode represents the bootstrap container mode. ++ // +kubebuilder:validation:Enum=always;off;once ++ Mode string `json:"mode"` ++ ++ // UserData is the base64-encoded userdata. ++ // +optional ++ UserData string `json:"userData,omitempty"` ++} ++ + // JoinControlPlane contains elements describing an additional control plane instance to be deployed on the joining node. + type JoinControlPlane struct { + // LocalAPIEndpoint represents the endpoint of the API server instance to be deployed on this node. +diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +index 8da1eb4c5..64e4eeff7 100644 +--- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +@@ -158,6 +158,22 @@ func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketBootstrapContainer) DeepCopyInto(out *BottlerocketBootstrapContainer) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootstrapContainer. ++func (in *BottlerocketBootstrapContainer) DeepCopy() *BottlerocketBootstrapContainer { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketBootstrapContainer) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketControl) DeepCopyInto(out *BottlerocketControl) { + *out = *in +@@ -217,6 +233,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = make([]BottlerocketHostContainer, len(*in)) + copy(*out, *in) + } ++ if in.BottlerocketCustomBootstrapContainers != nil { ++ in, out := &in.BottlerocketCustomBootstrapContainers, &out.BottlerocketCustomBootstrapContainers ++ *out = make([]BottlerocketBootstrapContainer, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. +@@ -640,6 +661,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = make([]BottlerocketHostContainer, len(*in)) + copy(*out, *in) + } ++ if in.BottlerocketCustomBootstrapContainers != nil { ++ in, out := &in.BottlerocketCustomBootstrapContainers, &out.BottlerocketCustomBootstrapContainers ++ *out = make([]BottlerocketBootstrapContainer, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +index b2b01cb68..b395ccd39 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +@@ -133,6 +133,48 @@ spec: + the version of the above components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers configured ++ with essential = true will stop the boot process if they ++ exit code is a non-zero value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that will ++ be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketHostContainers contains the information + of any additional images that we will deploy as host containers +@@ -803,6 +845,48 @@ spec: + the version of the above components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers configured ++ with essential = true will stop the boot process if they ++ exit code is a non-zero value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that will ++ be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketCustomHostContainers contains the information + of any additional images that we will deploy as host containers +@@ -1352,6 +1436,48 @@ spec: + the version of the above components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers configured ++ with essential = true will stop the boot process if they ++ exit code is a non-zero value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that will ++ be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketHostContainers contains the information + of any additional images that we will deploy as host containers +@@ -2018,6 +2144,48 @@ spec: + the version of the above components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers configured ++ with essential = true will stop the boot process if they ++ exit code is a non-zero value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that will ++ be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketCustomHostContainers contains the information + of any additional images that we will deploy as host containers +@@ -2565,6 +2733,48 @@ spec: + the version of the above components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers configured ++ with essential = true will stop the boot process if they ++ exit code is a non-zero value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that will ++ be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketHostContainers contains the information + of any additional images that we will deploy as host containers +@@ -3300,6 +3510,48 @@ spec: + the version of the above components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers configured ++ with essential = true will stop the boot process if they ++ exit code is a non-zero value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that will ++ be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketCustomHostContainers contains the information + of any additional images that we will deploy as host containers +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +index 311b5d79f..866c5de60 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +@@ -143,6 +143,53 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds ++ additional bootstrap containers for Bottlerocket. This ++ is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the ++ bootstrap container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the ++ container should fail the boot process. Bootstrap ++ containers configured with essential = true will ++ stop the boot process if they exit code is a non-zero ++ value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm ++ does not change automatically the version of the ++ above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name ++ that will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketHostContainers contains the information + of any additional images that we will deploy as host +@@ -853,6 +900,53 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds ++ additional bootstrap containers for Bottlerocket. This ++ is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the ++ bootstrap container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the ++ container should fail the boot process. Bootstrap ++ containers configured with essential = true will ++ stop the boot process if they exit code is a non-zero ++ value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm ++ does not change automatically the version of the ++ above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name ++ that will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketCustomHostContainers contains + the information of any additional images that we will +@@ -1362,6 +1456,53 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds ++ additional bootstrap containers for Bottlerocket. This ++ is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the ++ bootstrap container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the ++ container should fail the boot process. Bootstrap ++ containers configured with essential = true will ++ stop the boot process if they exit code is a non-zero ++ value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm ++ does not change automatically the version of the ++ above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name ++ that will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketHostContainers contains the information + of any additional images that we will deploy as host +@@ -2070,6 +2211,53 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds ++ additional bootstrap containers for Bottlerocket. This ++ is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the ++ bootstrap container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the ++ container should fail the boot process. Bootstrap ++ containers configured with essential = true will ++ stop the boot process if they exit code is a non-zero ++ value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm ++ does not change automatically the version of the ++ above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name ++ that will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketCustomHostContainers contains + the information of any additional images that we will +@@ -2602,6 +2790,53 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds ++ additional bootstrap containers for Bottlerocket. This ++ is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the ++ bootstrap container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the ++ container should fail the boot process. Bootstrap ++ containers configured with essential = true will ++ stop the boot process if they exit code is a non-zero ++ value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm ++ does not change automatically the version of the ++ above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name ++ that will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketHostContainers contains the information + of any additional images that we will deploy as host +@@ -3387,6 +3622,53 @@ spec: + components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds ++ additional bootstrap containers for Bottlerocket. This ++ is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the ++ bootstrap container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the ++ container should fail the boot process. Bootstrap ++ containers configured with essential = true will ++ stop the boot process if they exit code is a non-zero ++ value. Default is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm ++ does not change automatically the version of the ++ above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name ++ that will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketCustomHostContainers contains + the information of any additional images that we will +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +index bc5094eb1..fe280e091 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +@@ -34,6 +34,26 @@ user-data = "{{.UserData}}" + {{template "hostContainerSettings" $hContainer }} + {{- end -}} + {{- end -}} ++` ++ ++ bootstrapContainerTemplate = `{{ define "bootstrapContainerSettings" -}} ++[settings.bootstrap-containers.{{.Name}}] ++essential = {{.Essential}} ++mode = "{{.Mode}}" ++{{- if (ne (imageUrl .ImageMeta) "")}} ++source = "{{imageUrl .ImageMeta}}" ++{{- end -}} ++{{- if (ne .UserData "")}} ++user-data = "{{.UserData}}" ++{{- end -}} ++{{- end -}} ++` ++ ++ bootstrapContainerSliceTemplate = `{{ define "bootstrapContainerSlice" -}} ++{{- range $bContainer := .BootstrapContainers }} ++{{template "bootstrapContainerSettings" $bContainer }} ++{{- end -}} ++{{- end -}} + ` + + networkInitTemplate = `{{ define "networkInitSettings" -}} +@@ -68,6 +88,10 @@ trusted=true + + {{template "kubernetesInitSettings" .}} + ++{{- if .BootstrapContainers}} ++{{template "bootstrapContainerSlice" .}} ++{{- end -}} ++ + {{- if (ne .HTTPSProxyEndpoint "")}} + {{template "networkInitSettings" .}} + {{- end -}} +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +new file mode 100644 +index 000000000..9065a7c58 +--- /dev/null ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +@@ -0,0 +1,99 @@ ++package bottlerocket ++ ++import ( ++ "testing" ++ ++ . "github.com/onsi/gomega" ++ ++ bootstrapv1 "sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1" ++) ++ ++const userData = ` ++[settings.host-containers.admin] ++enabled = true ++superpowered = true ++user-data = "B64USERDATA" ++[settings.host-containers.kubeadm-bootstrap] ++enabled = true ++superpowered = true ++source = "REPO:TAG" ++user-data = "B64USERDATA" ++ ++[settings.kubernetes] ++cluster-domain = "cluster.local" ++standalone-mode = true ++authentication-mode = "tls" ++server-tls-bootstrap = false ++pod-infra-container-image = "PAUSE" ++provider-id = "PROVIDERID" ++ ++[settings.bootstrap-containers.BOOTSTRAP] ++essential = false ++mode = "MODE" ++user-data = "B64USERDATA" ++[settings.network] ++https-proxy = "PROXY" ++no-proxy = [] ++[settings.container-registry.mirrors] ++"public.ecr.aws" = ["https://REGISTRYENDPOINT"] ++[settings.pki.registry-mirror-ca] ++data = "REGISTRYCA" ++trusted=true ++[settings.kubernetes.node-labels] ++KEY=VAR ++[settings.kubernetes.node-taints] ++KEY=VAR` ++ ++func TestGenerateUserData(t *testing.T) { ++ g := NewWithT(t) ++ ++ testcases := []struct { ++ name string ++ input *BottlerocketSettingsInput ++ output string ++ }{ ++ { ++ name: "full settings", ++ input: &BottlerocketSettingsInput{ ++ PauseContainerSource: "PAUSE", ++ HTTPSProxyEndpoint: "PROXY", ++ RegistryMirrorEndpoint: "REGISTRYENDPOINT", ++ RegistryMirrorCACert: "REGISTRYCA", ++ NodeLabels: "KEY=VAR", ++ Taints: "KEY=VAR", ++ ProviderId: "PROVIDERID", ++ HostContainers: []bootstrapv1.BottlerocketHostContainer{ ++ { ++ Name: "admin", ++ Superpowered: true, ++ UserData: "B64USERDATA", ++ }, ++ { ++ Name: "kubeadm-bootstrap", ++ Superpowered: true, ++ ImageMeta: bootstrapv1.ImageMeta{ ++ ImageRepository: "REPO", ++ ImageTag: "TAG", ++ }, ++ UserData: "B64USERDATA", ++ }, ++ }, ++ BootstrapContainers: []bootstrapv1.BottlerocketBootstrapContainer{ ++ { ++ Name: "BOOTSTRAP", ++ Mode: "MODE", ++ UserData: "B64USERDATA", ++ }, ++ }, ++ }, ++ output: userData, ++ }, ++ } ++ for _, testcase := range testcases { ++ t.Run(testcase.name, func(t *testing.T) { ++ b, err := generateNodeUserData("TestBottlerocketInit", bottlerocketNodeInitSettingsTemplate, testcase.input) ++ g.Expect(err).NotTo(HaveOccurred()) ++ g.Expect(string(b)).To(Equal(testcase.output)) ++ }) ++ } ++} +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +index 0e6124b4c..e504684a0 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +@@ -23,14 +23,15 @@ const ( + ) + + type BottlerocketConfig struct { +- Pause bootstrapv1.Pause +- BottlerocketBootstrap bootstrapv1.BottlerocketBootstrap +- BottlerocketControl bootstrapv1.BottlerocketControl +- ProxyConfiguration bootstrapv1.ProxyConfiguration +- RegistryMirrorConfiguration bootstrapv1.RegistryMirrorConfiguration +- KubeletExtraArgs map[string]string +- Taints []corev1.Taint +- BottlerocketCustomHostContainers []bootstrapv1.BottlerocketHostContainer ++ Pause bootstrapv1.Pause ++ BottlerocketBootstrap bootstrapv1.BottlerocketBootstrap ++ BottlerocketControl bootstrapv1.BottlerocketControl ++ ProxyConfiguration bootstrapv1.ProxyConfiguration ++ RegistryMirrorConfiguration bootstrapv1.RegistryMirrorConfiguration ++ KubeletExtraArgs map[string]string ++ Taints []corev1.Taint ++ BottlerocketCustomHostContainers []bootstrapv1.BottlerocketHostContainer ++ BottlerocketCustomBootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer + } + + type BottlerocketSettingsInput struct { +@@ -43,6 +44,7 @@ type BottlerocketSettingsInput struct { + Taints string + ProviderId string + HostContainers []bootstrapv1.BottlerocketHostContainer ++ BootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer + } + + type HostPath struct { +@@ -103,6 +105,12 @@ func generateNodeUserData(kind string, tpl string, data interface{}) ([]byte, er + if _, err := tm.Parse(hostContainerSliceTemplate); err != nil { + return nil, errors.Wrapf(err, "failed to parse hostContainerSettingsSlice %s template", kind) + } ++ if _, err := tm.Parse(bootstrapContainerTemplate); err != nil { ++ return nil, errors.Wrapf(err, "failed to parse bootstrapContainerSettings %s template", kind) ++ } ++ if _, err := tm.Parse(bootstrapContainerSliceTemplate); err != nil { ++ return nil, errors.Wrapf(err, "failed to parse bootstrapContainerSettingsSlice %s template", kind) ++ } + if _, err := tm.Parse(kubernetesInitTemplate); err != nil { + return nil, errors.Wrapf(err, "failed to parse kubernetes %s template", kind) + } +@@ -179,9 +187,10 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot + HTTPSProxyEndpoint: config.ProxyConfiguration.HTTPSProxy, + RegistryMirrorEndpoint: config.RegistryMirrorConfiguration.Endpoint, + NodeLabels: parseNodeLabels(config.KubeletExtraArgs["node-labels"]), // empty string if it does not exist +- Taints: parseTaints(config.Taints), //empty string if it does not exist ++ Taints: parseTaints(config.Taints), // empty string if it does not exist + ProviderId: config.KubeletExtraArgs["provider-id"], + HostContainers: hostContainers, ++ BootstrapContainers: config.BottlerocketCustomBootstrapContainers, + } + + if len(config.ProxyConfiguration.NoProxy) > 0 { +diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go +index 8eb1d6c02..7cc63012c 100644 +--- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go ++++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go +@@ -473,10 +473,11 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex + } + + bottlerocketConfig = &bottlerocket.BottlerocketConfig{ +- Pause: scope.Config.Spec.ClusterConfiguration.Pause, +- BottlerocketBootstrap: scope.Config.Spec.ClusterConfiguration.BottlerocketBootstrap, +- BottlerocketControl: scope.Config.Spec.ClusterConfiguration.BottlerocketControl, +- BottlerocketCustomHostContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketHostContainers, ++ Pause: scope.Config.Spec.ClusterConfiguration.Pause, ++ BottlerocketBootstrap: scope.Config.Spec.ClusterConfiguration.BottlerocketBootstrap, ++ BottlerocketControl: scope.Config.Spec.ClusterConfiguration.BottlerocketControl, ++ BottlerocketCustomHostContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketHostContainers, ++ BottlerocketCustomBootstrapContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketCustomBootstrapContainers, + } + if scope.Config.Spec.ClusterConfiguration.Proxy.HTTPSProxy != "" { + bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.ClusterConfiguration.Proxy +@@ -679,10 +680,11 @@ func (r *KubeadmConfigReconciler) joinWorker(ctx context.Context, scope *Scope) + }) + case bootstrapv1.Bottlerocket: + bottlerocketConfig := &bottlerocket.BottlerocketConfig{ +- Pause: scope.Config.Spec.JoinConfiguration.Pause, +- BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, +- BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, +- BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, ++ Pause: scope.Config.Spec.JoinConfiguration.Pause, ++ BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, ++ BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, ++ BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, ++ BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, + } + if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { + bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy +@@ -807,10 +809,11 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S + }) + case bootstrapv1.Bottlerocket: + bottlerocketConfig := &bottlerocket.BottlerocketConfig{ +- Pause: scope.Config.Spec.JoinConfiguration.Pause, +- BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, +- BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, +- BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, ++ Pause: scope.Config.Spec.JoinConfiguration.Pause, ++ BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, ++ BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, ++ BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, ++ BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, + } + if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { + bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/types.go b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +index 2fb4e6e19..f35b90a43 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/types.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +@@ -154,6 +154,11 @@ type ClusterConfiguration struct { + // that we will deploy as host containers in the CPIs + // +optional + BottlerocketHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` ++ ++ // BottlerocketCustomBootstrapContainers adds additional bootstrap containers for Bottlerocket. ++ // This is only for bottlerocket. ++ // +optional ++ BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` + } + + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. +@@ -448,6 +453,11 @@ type JoinConfiguration struct { + // that we will deploy as host containers in the CPIs + // +optional + BottlerocketCustomHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` ++ ++ // BottlerocketCustomBootstrapContainers adds additional bootstrap containers for Bottlerocket. ++ // This is only for bottlerocket. ++ // +optional ++ BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` + } + + // BottlerocketHostContainer describes a host image for Bottlerocket +@@ -465,6 +475,29 @@ type BottlerocketHostContainer struct { + UserData string `json:"userData,omitempty"` + } + ++// BottlerocketBootstrapContainer holds the bootstrap container setting for Bottlerocket ++type BottlerocketBootstrapContainer struct { ++ // Name is the bootstrap container name that will be given to the container in BR's `apiserver`. ++ Name string `json:"name"` ++ ++ // ImageMeta is the actual image used for Bottlerocket bootstrap. ++ ImageMeta `json:",inline"` ++ ++ // Essential decides whether or not the container should fail the boot process. ++ // Bootstrap containers configured with essential = true will stop the boot process if they exit code is a non-zero value. ++ // Default is false. ++ // +optional ++ Essential bool `json:"essential"` ++ ++ // Mode represents the bootstrap container mode. ++ // +kubebuilder:validation:Enum=always;off;once ++ Mode string `json:"mode"` ++ ++ // UserData is the base64-encoded userdata. ++ // +optional ++ UserData string `json:"userData,omitempty"` ++} ++ + // JoinControlPlane contains elements describing an additional control plane instance to be deployed on the joining node. + type JoinControlPlane struct { + // LocalAPIEndpoint represents the endpoint of the API server instance to be deployed on this node. +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +index 03d4640e6..531086227 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +@@ -157,6 +157,22 @@ func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketBootstrapContainer) DeepCopyInto(out *BottlerocketBootstrapContainer) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootstrapContainer. ++func (in *BottlerocketBootstrapContainer) DeepCopy() *BottlerocketBootstrapContainer { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketBootstrapContainer) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketControl) DeepCopyInto(out *BottlerocketControl) { + *out = *in +@@ -216,6 +232,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = make([]BottlerocketHostContainer, len(*in)) + copy(*out, *in) + } ++ if in.BottlerocketCustomBootstrapContainers != nil { ++ in, out := &in.BottlerocketCustomBootstrapContainers, &out.BottlerocketCustomBootstrapContainers ++ *out = make([]BottlerocketBootstrapContainer, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. +@@ -484,6 +505,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = make([]BottlerocketHostContainer, len(*in)) + copy(*out, *in) + } ++ if in.BottlerocketCustomBootstrapContainers != nil { ++ in, out := &in.BottlerocketCustomBootstrapContainers, &out.BottlerocketCustomBootstrapContainers ++ *out = make([]BottlerocketBootstrapContainer, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. +diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go +index 6b4eac17b..2e3bc99ea 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go +@@ -562,6 +562,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta2_ClusterConfigur + out.FeatureGates = *(*map[string]bool)(unsafe.Pointer(&in.FeatureGates)) + out.ClusterName = in.ClusterName + // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type ++ // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type + return nil + } + +@@ -871,6 +872,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta2_JoinConfiguration( + // WARNING: in.SkipPhases requires manual conversion: does not exist in peer-type + // WARNING: in.Patches requires manual conversion: does not exist in peer-type + // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type ++ // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type + return nil + } + +diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go +index d290e4d94..1b2d94a1d 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go +@@ -566,6 +566,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta3_ClusterConfigur + out.FeatureGates = *(*map[string]bool)(unsafe.Pointer(&in.FeatureGates)) + out.ClusterName = in.ClusterName + // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type ++ // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type + return nil + } + +@@ -863,6 +864,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta3_JoinConfiguration( + out.SkipPhases = *(*[]string)(unsafe.Pointer(&in.SkipPhases)) + out.Patches = (*Patches)(unsafe.Pointer(in.Patches)) + // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type ++ // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type + return nil + } + +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +index 77ca12b3b..83e45839a 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +@@ -210,6 +210,52 @@ spec: + upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for ++ bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers ++ configured with essential = true will stop the boot ++ process if they exit code is a non-zero value. Default ++ is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not ++ change automatically the version of the above components ++ during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that ++ will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketHostContainers contains the information + of any additional images that we will deploy as host containers +@@ -905,6 +951,52 @@ spec: + upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for ++ bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers ++ configured with essential = true will stop the boot ++ process if they exit code is a non-zero value. Default ++ is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not ++ change automatically the version of the above components ++ during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that ++ will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketCustomHostContainers contains the + information of any additional images that we will deploy +@@ -1586,6 +1678,52 @@ spec: + upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for ++ bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers ++ configured with essential = true will stop the boot ++ process if they exit code is a non-zero value. Default ++ is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not ++ change automatically the version of the above components ++ during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that ++ will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketHostContainers contains the information + of any additional images that we will deploy as host containers +@@ -2278,6 +2416,52 @@ spec: + upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for ++ bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers ++ configured with essential = true will stop the boot ++ process if they exit code is a non-zero value. Default ++ is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not ++ change automatically the version of the above components ++ during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that ++ will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketCustomHostContainers contains the + information of any additional images that we will deploy +@@ -3043,6 +3227,52 @@ spec: + upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for ++ bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers ++ configured with essential = true will stop the boot ++ process if they exit code is a non-zero value. Default ++ is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not ++ change automatically the version of the above components ++ during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that ++ will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketHostContainers contains the information + of any additional images that we will deploy as host containers +@@ -3808,6 +4038,52 @@ spec: + upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers adds additional ++ bootstrap containers for Bottlerocket. This is only for ++ bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds the bootstrap ++ container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not the container ++ should fail the boot process. Bootstrap containers ++ configured with essential = true will stop the boot ++ process if they exit code is a non-zero value. Default ++ is false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not ++ change automatically the version of the above components ++ during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container name that ++ will be given to the container in BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketCustomHostContainers contains the + information of any additional images that we will deploy +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +index 2f9941558..8ddae49c7 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +@@ -160,6 +160,56 @@ spec: + the above components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers ++ adds additional bootstrap containers for Bottlerocket. ++ This is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds ++ the bootstrap container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not ++ the container should fail the boot process. ++ Bootstrap containers configured with essential ++ = true will stop the boot process if they ++ exit code is a non-zero value. Default is ++ false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, ++ kubeadm does not change automatically the ++ version of the above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container ++ name that will be given to the container in ++ BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded ++ userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketHostContainers contains the + information of any additional images that we will +@@ -898,6 +948,56 @@ spec: + the above components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers ++ adds additional bootstrap containers for Bottlerocket. ++ This is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds ++ the bootstrap container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not ++ the container should fail the boot process. ++ Bootstrap containers configured with essential ++ = true will stop the boot process if they ++ exit code is a non-zero value. Default is ++ false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, ++ kubeadm does not change automatically the ++ version of the above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container ++ name that will be given to the container in ++ BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded ++ userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketCustomHostContainers contains + the information of any additional images that we +@@ -1593,6 +1693,56 @@ spec: + the above components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers ++ adds additional bootstrap containers for Bottlerocket. ++ This is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds ++ the bootstrap container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not ++ the container should fail the boot process. ++ Bootstrap containers configured with essential ++ = true will stop the boot process if they ++ exit code is a non-zero value. Default is ++ false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, ++ kubeadm does not change automatically the ++ version of the above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container ++ name that will be given to the container in ++ BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded ++ userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketHostContainers contains the + information of any additional images that we will +@@ -2410,6 +2560,56 @@ spec: + the above components during upgrades. + type: string + type: object ++ bottlerocketCustomBootstrapContainers: ++ description: BottlerocketCustomBootstrapContainers ++ adds additional bootstrap containers for Bottlerocket. ++ This is only for bottlerocket. ++ items: ++ description: BottlerocketBootstrapContainer holds ++ the bootstrap container setting for Bottlerocket ++ properties: ++ essential: ++ description: Essential decides whether or not ++ the container should fail the boot process. ++ Bootstrap containers configured with essential ++ = true will stop the boot process if they ++ exit code is a non-zero value. Default is ++ false. ++ type: boolean ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, ++ the ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, ++ kubeadm does not change automatically the ++ version of the above components during upgrades. ++ type: string ++ mode: ++ description: Mode represents the bootstrap container ++ mode. ++ enum: ++ - always ++ - "off" ++ - once ++ type: string ++ name: ++ description: Name is the bootstrap container ++ name that will be given to the container in ++ BR's `apiserver`. ++ type: string ++ userData: ++ description: UserData is the base64-encoded ++ userdata. ++ type: string ++ required: ++ - mode ++ - name ++ type: object ++ type: array + bottlerocketCustomHostContainers: + description: BottlerocketCustomHostContainers contains + the information of any additional images that we +-- +2.42.0 + diff --git a/projects/kubernetes-sigs/cluster-api/patches/0019-Support-configuring-bottlerocket-admin-container-ima.patch b/projects/kubernetes-sigs/cluster-api/patches/0019-Support-configuring-bottlerocket-admin-container-ima.patch new file mode 100644 index 0000000000..f3dcee0c02 --- /dev/null +++ b/projects/kubernetes-sigs/cluster-api/patches/0019-Support-configuring-bottlerocket-admin-container-ima.patch @@ -0,0 +1,1089 @@ +From 53074d3ab3f3bdd81b4679ff14636289f28f22cc Mon Sep 17 00:00:00 2001 +From: Jiayi Wang +Date: Wed, 23 Nov 2022 09:26:28 -0500 +Subject: [PATCH 19/40] Support configuring bottlerocket admin container image + +--- + .../kubeadm/api/v1alpha4/kubeadm_types.go | 17 ++++ + .../api/v1alpha4/zz_generated.conversion.go | 46 +++++++++ + .../api/v1alpha4/zz_generated.deepcopy.go | 18 ++++ + .../kubeadm/api/v1beta1/kubeadm_types.go | 17 ++++ + .../api/v1beta1/zz_generated.deepcopy.go | 18 ++++ + ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 90 +++++++++++++++++ + ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 96 +++++++++++++++++++ + .../internal/bottlerocket/bootstrap_test.go | 82 +++++++++++++++- + .../internal/bottlerocket/bottlerocket.go | 2 + + .../controllers/kubeadmconfig_controller.go | 3 + + .../kubeadm/types/upstreamv1beta1/types.go | 17 ++++ + .../upstreamv1beta1/zz_generated.deepcopy.go | 18 ++++ + .../zz_generated.conversion.go | 2 + + .../zz_generated.conversion.go | 2 + + ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 96 +++++++++++++++++++ + ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 68 +++++++++++++ + 16 files changed, 590 insertions(+), 2 deletions(-) + +diff --git a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +index 592c257b8..f1e5eee19 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +@@ -71,6 +71,11 @@ type ClusterConfiguration struct { + // +optional + BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` + ++ // BottlerocketAdmin holds the image source for admin container ++ // This is only for bottlerocket ++ // +optional ++ BottlerocketAdmin BottlerocketAdmin `json:"bottlerocketAdmin,omitempty"` ++ + // BottlerocketControl holds the image source for control container + // This is only for bottlerocket + // +optional +@@ -177,6 +182,13 @@ type BottlerocketBootstrap struct { + ImageMeta `json:",inline"` + } + ++// BottlerocketAdmin holds the settings of admin container for bottlerocket nodes ++// This setting is ONLY for bottlerocket nodes. ++type BottlerocketAdmin struct { ++ // ImageMeta allows to customize the image used for the BottlerocketAdmin component ++ ImageMeta `json:",inline"` ++} ++ + // BottlerocketControl holds the settings of control container for bottlerocket nodes + // This setting is ONLY for bottlerocket nodes. + type BottlerocketControl struct { +@@ -422,6 +434,11 @@ type JoinConfiguration struct { + // +optional + BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` + ++ // BottlerocketAdmin holds the image source for admin container ++ // This is only for bottlerocket ++ // +optional ++ BottlerocketAdmin BottlerocketAdmin `json:"bottlerocketAdmin,omitempty"` ++ + // BottlerocketControl holds the image source for control container + // This is only for bottlerocket + // +optional +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +index 2b70d0c11..c3bdb3831 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +@@ -90,6 +90,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketAdmin)(nil), (*v1beta1.BottlerocketAdmin)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(a.(*BottlerocketAdmin), b.(*v1beta1.BottlerocketAdmin), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketAdmin)(nil), (*BottlerocketAdmin)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketAdmin_To_v1alpha4_BottlerocketAdmin(a.(*v1beta1.BottlerocketAdmin), b.(*BottlerocketAdmin), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrap)(nil), (*v1beta1.BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(a.(*BottlerocketBootstrap), b.(*v1beta1.BottlerocketBootstrap), scope) + }); err != nil { +@@ -611,6 +621,30 @@ func Convert_v1beta1_BootstrapTokenString_To_v1alpha4_BootstrapTokenString(in *v + return autoConvert_v1beta1_BootstrapTokenString_To_v1alpha4_BootstrapTokenString(in, out, s) + } + ++func autoConvert_v1alpha4_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(in *BottlerocketAdmin, out *v1beta1.BottlerocketAdmin, s conversion.Scope) error { ++ if err := Convert_v1alpha4_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1alpha4_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin is an autogenerated conversion function. ++func Convert_v1alpha4_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(in *BottlerocketAdmin, out *v1beta1.BottlerocketAdmin, s conversion.Scope) error { ++ return autoConvert_v1alpha4_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketAdmin_To_v1alpha4_BottlerocketAdmin(in *v1beta1.BottlerocketAdmin, out *BottlerocketAdmin, s conversion.Scope) error { ++ if err := Convert_v1beta1_ImageMeta_To_v1alpha4_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketAdmin_To_v1alpha4_BottlerocketAdmin is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketAdmin_To_v1alpha4_BottlerocketAdmin(in *v1beta1.BottlerocketAdmin, out *BottlerocketAdmin, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketAdmin_To_v1alpha4_BottlerocketAdmin(in, out, s) ++} ++ + func autoConvert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { + if err := Convert_v1alpha4_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { + return err +@@ -728,6 +762,9 @@ func autoConvert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(i + if err := Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { + return err + } ++ if err := Convert_v1alpha4_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(&in.BottlerocketAdmin, &out.BottlerocketAdmin, s); err != nil { ++ return err ++ } + if err := Convert_v1alpha4_BottlerocketControl_To_v1beta1_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { + return err + } +@@ -778,6 +815,9 @@ func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(i + if err := Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { + return err + } ++ if err := Convert_v1beta1_BottlerocketAdmin_To_v1alpha4_BottlerocketAdmin(&in.BottlerocketAdmin, &out.BottlerocketAdmin, s); err != nil { ++ return err ++ } + if err := Convert_v1beta1_BottlerocketControl_To_v1alpha4_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { + return err + } +@@ -1166,6 +1206,9 @@ func autoConvert_v1alpha4_JoinConfiguration_To_v1beta1_JoinConfiguration(in *Joi + if err := Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { + return err + } ++ if err := Convert_v1alpha4_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(&in.BottlerocketAdmin, &out.BottlerocketAdmin, s); err != nil { ++ return err ++ } + if err := Convert_v1alpha4_BottlerocketControl_To_v1beta1_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { + return err + } +@@ -1200,6 +1243,9 @@ func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1b + if err := Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { + return err + } ++ if err := Convert_v1beta1_BottlerocketAdmin_To_v1alpha4_BottlerocketAdmin(&in.BottlerocketAdmin, &out.BottlerocketAdmin, s); err != nil { ++ return err ++ } + if err := Convert_v1beta1_BottlerocketControl_To_v1alpha4_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { + return err + } +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +index c7f644c8f..4688180f0 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +@@ -142,6 +142,22 @@ func (in *BootstrapTokenString) DeepCopy() *BootstrapTokenString { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketAdmin) DeepCopyInto(out *BottlerocketAdmin) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketAdmin. ++func (in *BottlerocketAdmin) DeepCopy() *BottlerocketAdmin { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketAdmin) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { + *out = *in +@@ -212,6 +228,7 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + out.TypeMeta = in.TypeMeta + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror +@@ -591,6 +608,7 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + out.TypeMeta = in.TypeMeta + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror +diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +index 48e5f4b8e..409d724b3 100644 +--- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +@@ -83,6 +83,11 @@ type ClusterConfiguration struct { + // +optional + BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` + ++ // BottlerocketAdmin holds the image source for admin container ++ // This is only for bottlerocket ++ // +optional ++ BottlerocketAdmin BottlerocketAdmin `json:"bottlerocketAdmin,omitempty"` ++ + // BottlerocketControl holds the image source for control container + // This is only for bottlerocket + // +optional +@@ -196,6 +201,13 @@ type BottlerocketBootstrap struct { + ImageMeta `json:",inline"` + } + ++// BottlerocketAdmin holds the settings of admin container for bottlerocket nodes ++// This setting is ONLY for bottlerocket nodes. ++type BottlerocketAdmin struct { ++ // ImageMeta allows to customize the image used for the BottlerocketAdmin component ++ ImageMeta `json:",inline"` ++} ++ + // BottlerocketControl holds the settings of control container for bottlerocket nodes + // This setting is ONLY for bottlerocket nodes. + type BottlerocketControl struct { +@@ -498,6 +510,11 @@ type JoinConfiguration struct { + // +optional + BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` + ++ // BottlerocketAdmin holds the image source for admin container ++ // This is only for bottlerocket ++ // +optional ++ BottlerocketAdmin BottlerocketAdmin `json:"bottlerocketAdmin,omitempty"` ++ + // BottlerocketControl holds the image source for control container + // This is only for bottlerocket + // +optional +diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +index 64e4eeff7..ca5525885 100644 +--- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +@@ -142,6 +142,22 @@ func (in *BootstrapTokenString) DeepCopy() *BootstrapTokenString { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketAdmin) DeepCopyInto(out *BottlerocketAdmin) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketAdmin. ++func (in *BottlerocketAdmin) DeepCopy() *BottlerocketAdmin { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketAdmin) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { + *out = *in +@@ -212,6 +228,7 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + out.TypeMeta = in.TypeMeta + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror +@@ -636,6 +653,7 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + out.TypeMeta = in.TypeMeta + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +index b395ccd39..aad4846c8 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +@@ -103,6 +103,21 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for admin ++ container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source for + kubeadm bootstrap container This is only for bottlerocket +@@ -815,6 +830,21 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for admin ++ container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source for + kubeadm bootstrap container This is only for bottlerocket +@@ -1406,6 +1436,21 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for admin ++ container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source for + kubeadm bootstrap container This is only for bottlerocket +@@ -2114,6 +2159,21 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for admin ++ container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source for + kubeadm bootstrap container This is only for bottlerocket +@@ -2703,6 +2763,21 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for admin ++ container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source for + kubeadm bootstrap container This is only for bottlerocket +@@ -3480,6 +3555,21 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for admin ++ container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry to ++ pull images from. if not set, the ImageRepository defined ++ in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the image. ++ In case this value is set, kubeadm does not change automatically ++ the version of the above components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source for + kubeadm bootstrap container This is only for bottlerocket +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +index 866c5de60..67d0f44e5 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +@@ -111,6 +111,22 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source ++ for admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +@@ -868,6 +884,22 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source ++ for admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +@@ -1424,6 +1456,22 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source ++ for admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +@@ -2179,6 +2227,22 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source ++ for admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +@@ -2758,6 +2822,22 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source ++ for admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +@@ -3590,6 +3670,22 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source ++ for admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for ++ the image. In case this value is set, kubeadm does ++ not change automatically the version of the above ++ components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +index 9065a7c58..5ee1b0d45 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +@@ -8,7 +8,44 @@ import ( + bootstrapv1 "sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1" + ) + +-const userData = ` ++const userDataFullSetting = ` ++[settings.host-containers.admin] ++enabled = true ++superpowered = true ++source = "REPO:TAG" ++user-data = "B64USERDATA" ++[settings.host-containers.kubeadm-bootstrap] ++enabled = true ++superpowered = true ++source = "REPO:TAG" ++user-data = "B64USERDATA" ++ ++[settings.kubernetes] ++cluster-domain = "cluster.local" ++standalone-mode = true ++authentication-mode = "tls" ++server-tls-bootstrap = false ++pod-infra-container-image = "PAUSE" ++provider-id = "PROVIDERID" ++ ++[settings.bootstrap-containers.BOOTSTRAP] ++essential = false ++mode = "MODE" ++user-data = "B64USERDATA" ++[settings.network] ++https-proxy = "PROXY" ++no-proxy = [] ++[settings.container-registry.mirrors] ++"public.ecr.aws" = ["https://REGISTRYENDPOINT"] ++[settings.pki.registry-mirror-ca] ++data = "REGISTRYCA" ++trusted=true ++[settings.kubernetes.node-labels] ++KEY=VAR ++[settings.kubernetes.node-taints] ++KEY=VAR` ++ ++const userDataNoAdminImage = ` + [settings.host-containers.admin] + enabled = true + superpowered = true +@@ -66,6 +103,47 @@ func TestGenerateUserData(t *testing.T) { + { + Name: "admin", + Superpowered: true, ++ ImageMeta: bootstrapv1.ImageMeta{ ++ ImageRepository: "REPO", ++ ImageTag: "TAG", ++ }, ++ UserData: "B64USERDATA", ++ }, ++ { ++ Name: "kubeadm-bootstrap", ++ Superpowered: true, ++ ImageMeta: bootstrapv1.ImageMeta{ ++ ImageRepository: "REPO", ++ ImageTag: "TAG", ++ }, ++ UserData: "B64USERDATA", ++ }, ++ }, ++ BootstrapContainers: []bootstrapv1.BottlerocketBootstrapContainer{ ++ { ++ Name: "BOOTSTRAP", ++ Mode: "MODE", ++ UserData: "B64USERDATA", ++ }, ++ }, ++ }, ++ output: userDataFullSetting, ++ }, ++ { ++ name: "no admin image meta", ++ input: &BottlerocketSettingsInput{ ++ PauseContainerSource: "PAUSE", ++ HTTPSProxyEndpoint: "PROXY", ++ RegistryMirrorEndpoint: "REGISTRYENDPOINT", ++ RegistryMirrorCACert: "REGISTRYCA", ++ NodeLabels: "KEY=VAR", ++ Taints: "KEY=VAR", ++ ProviderId: "PROVIDERID", ++ HostContainers: []bootstrapv1.BottlerocketHostContainer{ ++ { ++ Name: "admin", ++ Superpowered: true, ++ ImageMeta: bootstrapv1.ImageMeta{}, + UserData: "B64USERDATA", + }, + { +@@ -86,7 +164,7 @@ func TestGenerateUserData(t *testing.T) { + }, + }, + }, +- output: userData, ++ output: userDataNoAdminImage, + }, + } + for _, testcase := range testcases { +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +index e504684a0..9848f47e8 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +@@ -25,6 +25,7 @@ const ( + type BottlerocketConfig struct { + Pause bootstrapv1.Pause + BottlerocketBootstrap bootstrapv1.BottlerocketBootstrap ++ BottlerocketAdmin bootstrapv1.BottlerocketAdmin + BottlerocketControl bootstrapv1.BottlerocketControl + ProxyConfiguration bootstrapv1.ProxyConfiguration + RegistryMirrorConfiguration bootstrapv1.RegistryMirrorConfiguration +@@ -160,6 +161,7 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot + { + Name: "admin", + Superpowered: true, ++ ImageMeta: config.BottlerocketAdmin.ImageMeta, + UserData: b64AdminContainerUserData, + }, + { +diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go +index 7cc63012c..f4f3624c4 100644 +--- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go ++++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go +@@ -475,6 +475,7 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex + bottlerocketConfig = &bottlerocket.BottlerocketConfig{ + Pause: scope.Config.Spec.ClusterConfiguration.Pause, + BottlerocketBootstrap: scope.Config.Spec.ClusterConfiguration.BottlerocketBootstrap, ++ BottlerocketAdmin: scope.Config.Spec.ClusterConfiguration.BottlerocketAdmin, + BottlerocketControl: scope.Config.Spec.ClusterConfiguration.BottlerocketControl, + BottlerocketCustomHostContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketHostContainers, + BottlerocketCustomBootstrapContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketCustomBootstrapContainers, +@@ -682,6 +683,7 @@ func (r *KubeadmConfigReconciler) joinWorker(ctx context.Context, scope *Scope) + bottlerocketConfig := &bottlerocket.BottlerocketConfig{ + Pause: scope.Config.Spec.JoinConfiguration.Pause, + BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, ++ BottlerocketAdmin: scope.Config.Spec.JoinConfiguration.BottlerocketAdmin, + BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, + BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, + BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, +@@ -811,6 +813,7 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S + bottlerocketConfig := &bottlerocket.BottlerocketConfig{ + Pause: scope.Config.Spec.JoinConfiguration.Pause, + BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, ++ BottlerocketAdmin: scope.Config.Spec.JoinConfiguration.BottlerocketAdmin, + BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, + BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, + BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/types.go b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +index f35b90a43..43b0bf856 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/types.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +@@ -65,6 +65,11 @@ type ClusterConfiguration struct { + // +optional + BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` + ++ // BottlerocketAdmin holds the image source for admin container ++ // This is only for bottlerocket ++ // +optional ++ BottlerocketAdmin BottlerocketAdmin `json:"bottlerocketAdmin,omitempty"` ++ + // BottlerocketControl holds the image source for control container + // This is only for bottlerocket + // +optional +@@ -175,6 +180,13 @@ type BottlerocketBootstrap struct { + ImageMeta `json:",inline"` + } + ++// BottlerocketAdmin holds the settings of admin container for bottlerocket nodes ++// This setting is ONLY for bottlerocket nodes. ++type BottlerocketAdmin struct { ++ // ImageMeta allows to customize the image used for the BottlerocketAdmin component ++ ImageMeta `json:",inline"` ++} ++ + // BottlerocketControl holds the settings of control container for bottlerocket nodes + // This setting is ONLY for bottlerocket nodes. + type BottlerocketControl struct { +@@ -411,6 +423,11 @@ type JoinConfiguration struct { + // +optional + BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` + ++ // BottlerocketAdmin holds the image source for admin container ++ // This is only for bottlerocket ++ // +optional ++ BottlerocketAdmin BottlerocketAdmin `json:"bottlerocketAdmin,omitempty"` ++ + // BottlerocketControl holds the image source for control container + // This is only for bottlerocket + // +optional +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +index 531086227..ecbb70ea6 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +@@ -141,6 +141,22 @@ func (in *BootstrapTokenString) DeepCopy() *BootstrapTokenString { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketAdmin) DeepCopyInto(out *BottlerocketAdmin) { ++ *out = *in ++ out.ImageMeta = in.ImageMeta ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketAdmin. ++func (in *BottlerocketAdmin) DeepCopy() *BottlerocketAdmin { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketAdmin) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { + *out = *in +@@ -211,6 +227,7 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + out.TypeMeta = in.TypeMeta + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror +@@ -490,6 +507,7 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + out.TypeMeta = in.TypeMeta + out.Pause = in.Pause + out.BottlerocketBootstrap = in.BottlerocketBootstrap ++ out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) + out.RegistryMirror = in.RegistryMirror +diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go +index 2e3bc99ea..8b6475592 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go +@@ -528,6 +528,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta2_ClusterConfigur + if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { + return err + } ++ // WARNING: in.BottlerocketAdmin requires manual conversion: does not exist in peer-type + if err := Convert_v1beta1_BottlerocketControl_To_upstreamv1beta2_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { + return err + } +@@ -844,6 +845,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta2_JoinConfiguration( + if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { + return err + } ++ // WARNING: in.BottlerocketAdmin requires manual conversion: does not exist in peer-type + if err := Convert_v1beta1_BottlerocketControl_To_upstreamv1beta2_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { + return err + } +diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go +index 1b2d94a1d..4584e6266 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go +@@ -532,6 +532,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta3_ClusterConfigur + if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { + return err + } ++ // WARNING: in.BottlerocketAdmin requires manual conversion: does not exist in peer-type + if err := Convert_v1beta1_BottlerocketControl_To_upstreamv1beta3_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { + return err + } +@@ -836,6 +837,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta3_JoinConfiguration( + if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { + return err + } ++ // WARNING: in.BottlerocketAdmin requires manual conversion: does not exist in peer-type + if err := Convert_v1beta1_BottlerocketControl_To_upstreamv1beta3_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { + return err + } +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +index 83e45839a..119558689 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +@@ -178,6 +178,22 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for ++ admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +@@ -919,6 +935,22 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for ++ admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +@@ -1646,6 +1678,22 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for ++ admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +@@ -2384,6 +2432,22 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for ++ admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +@@ -3195,6 +3259,22 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for ++ admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +@@ -4006,6 +4086,22 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source for ++ admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container registry ++ to pull images from. if not set, the ImageRepository ++ defined in ClusterConfiguration will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag for the ++ image. In case this value is set, kubeadm does not change ++ automatically the version of the above components during ++ upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image source + for kubeadm bootstrap container This is only for bottlerocket +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +index 8ddae49c7..66e39e74a 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +@@ -125,6 +125,23 @@ spec: + value, and may reject unrecognized values. More + info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source ++ for admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, kubeadm ++ does not change automatically the version of ++ the above components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image + source for kubeadm bootstrap container This is only +@@ -913,6 +930,23 @@ spec: + value, and may reject unrecognized values. More + info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source ++ for admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, kubeadm ++ does not change automatically the version of ++ the above components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image + source for kubeadm bootstrap container This is only +@@ -1658,6 +1692,23 @@ spec: + value, and may reject unrecognized values. More + info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source ++ for admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, kubeadm ++ does not change automatically the version of ++ the above components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image + source for kubeadm bootstrap container This is only +@@ -2525,6 +2576,23 @@ spec: + value, and may reject unrecognized values. More + info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocketAdmin: ++ description: BottlerocketAdmin holds the image source ++ for admin container This is only for bottlerocket ++ properties: ++ imageRepository: ++ description: ImageRepository sets the container ++ registry to pull images from. if not set, the ++ ImageRepository defined in ClusterConfiguration ++ will be used instead. ++ type: string ++ imageTag: ++ description: ImageTag allows to specify a tag ++ for the image. In case this value is set, kubeadm ++ does not change automatically the version of ++ the above components during upgrades. ++ type: string ++ type: object + bottlerocketBootstrap: + description: BottlerocketBootstrap holds the image + source for kubeadm bootstrap container This is only +-- +2.42.0 + diff --git a/projects/kubernetes-sigs/cluster-api/patches/0020-Add-bottlerocket-custom-bootstrap-containers-config-.patch b/projects/kubernetes-sigs/cluster-api/patches/0020-Add-bottlerocket-custom-bootstrap-containers-config-.patch deleted file mode 100644 index 3adbacbf68..0000000000 --- a/projects/kubernetes-sigs/cluster-api/patches/0020-Add-bottlerocket-custom-bootstrap-containers-config-.patch +++ /dev/null @@ -1,932 +0,0 @@ -From c3105aa43984b94e30eabc15aaded418f59e97a9 Mon Sep 17 00:00:00 2001 -From: Jiayi Wang -Date: Mon, 21 Nov 2022 17:31:22 -0500 -Subject: [PATCH 20/40] Add bottlerocket custom bootstrap containers config - option - ---- - .../api/v1alpha4/zz_generated.conversion.go | 10 +- - .../kubeadm/api/v1beta1/kubeadm_types.go | 36 ++++++- - .../api/v1beta1/zz_generated.deepcopy.go | 26 +++++ - ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 84 +++++++++++++++ - ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 94 ++++++++++++++++ - .../internal/bottlerocket/bootstrap.go | 24 +++++ - .../internal/bottlerocket/bootstrap_test.go | 99 +++++++++++++++++ - .../internal/bottlerocket/bottlerocket.go | 27 +++-- - .../controllers/kubeadmconfig_controller.go | 27 ++--- - .../zz_generated.conversion.go | 2 + - .../zz_generated.conversion.go | 2 + - ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 92 ++++++++++++++++ - ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 100 ++++++++++++++++++ - 13 files changed, 596 insertions(+), 27 deletions(-) - create mode 100644 bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go - -diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -index fcea82a30..de8032f59 100644 ---- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -@@ -420,13 +420,13 @@ func RegisterConversions(s *runtime.Scheme) error { - }); err != nil { - return err - } -- if err := s.AddConversionFunc((*v1beta1.File)(nil), (*File)(nil), func(a, b interface{}, scope conversion.Scope) error { -- return Convert_v1beta1_File_To_v1alpha4_File(a.(*v1beta1.File), b.(*File), scope) -+ if err := s.AddConversionFunc((*v1beta1.ClusterConfiguration)(nil), (*ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(a.(*v1beta1.ClusterConfiguration), b.(*ClusterConfiguration), scope) - }); err != nil { - return err - } -- if err := s.AddConversionFunc((*v1beta1.ClusterConfiguration)(nil), (*ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { -- return Convert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(a.(*v1beta1.ClusterConfiguration), b.(*ClusterConfiguration), scope) -+ if err := s.AddConversionFunc((*v1beta1.File)(nil), (*File)(nil), func(a, b interface{}, scope conversion.Scope) error { -+ return Convert_v1beta1_File_To_v1alpha4_File(a.(*v1beta1.File), b.(*File), scope) - }); err != nil { - return err - } -@@ -728,6 +728,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(i - out.FeatureGates = *(*map[string]bool)(unsafe.Pointer(&in.FeatureGates)) - out.ClusterName = in.ClusterName - // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type -+ // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - return nil - } - -@@ -1133,6 +1134,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1b - // WARNING: in.SkipPhases requires manual conversion: does not exist in peer-type - // WARNING: in.Patches requires manual conversion: does not exist in peer-type - // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type -+ // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - return nil - } - -diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -index 44ffa00f3..48e5f4b8e 100644 ---- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -+++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -@@ -175,6 +175,11 @@ type ClusterConfiguration struct { - // that we will deploy as host containers in the CPIs - // +optional - BottlerocketHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` -+ -+ // BottlerocketCustomBootstrapContainers adds additional bootstrap containers for Bottlerocket. -+ // This is only for bottlerocket. -+ // +optional -+ BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` - } - - // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. -@@ -261,7 +266,7 @@ type ImageMeta struct { - // +optional - ImageTag string `json:"imageTag,omitempty"` - -- //TODO: evaluate if we need also a ImageName based on user feedbacks -+ // TODO: evaluate if we need also a ImageName based on user feedbacks - } - - // +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object -@@ -424,7 +429,6 @@ type BootstrapToken struct { - - // Etcd contains elements describing Etcd configuration. - type Etcd struct { -- - // Local provides configuration knobs for configuring the local etcd instance - // Local and External are mutually exclusive - // +optional -@@ -547,6 +551,11 @@ type JoinConfiguration struct { - // that we will deploy as host containers in the CPIs - // +optional - BottlerocketCustomHostContainers []BottlerocketHostContainer `json:"bottlerocketCustomHostContainers,omitempty"` -+ -+ // BottlerocketCustomBootstrapContainers adds additional bootstrap containers for Bottlerocket. -+ // This is only for bottlerocket. -+ // +optional -+ BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` - } - - // BottlerocketHostContainer describes a host image for Bottlerocket -@@ -564,6 +573,29 @@ type BottlerocketHostContainer struct { - UserData string `json:"userData,omitempty"` - } - -+// BottlerocketBootstrapContainer holds the bootstrap container setting for Bottlerocket -+type BottlerocketBootstrapContainer struct { -+ // Name is the bootstrap container name that will be given to the container in BR's `apiserver`. -+ Name string `json:"name"` -+ -+ // ImageMeta is the actual image used for Bottlerocket bootstrap. -+ ImageMeta `json:",inline"` -+ -+ // Essential decides whether or not the container should fail the boot process. -+ // Bootstrap containers configured with essential = true will stop the boot process if they exit code is a non-zero value. -+ // Default is false. -+ // +optional -+ Essential bool `json:"essential"` -+ -+ // Mode represents the bootstrap container mode. -+ // +kubebuilder:validation:Enum=always;off;once -+ Mode string `json:"mode"` -+ -+ // UserData is the base64-encoded userdata. -+ // +optional -+ UserData string `json:"userData,omitempty"` -+} -+ - // JoinControlPlane contains elements describing an additional control plane instance to be deployed on the joining node. - type JoinControlPlane struct { - // LocalAPIEndpoint represents the endpoint of the API server instance to be deployed on this node. -diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -index 8da1eb4c5..64e4eeff7 100644 ---- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -+++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -@@ -158,6 +158,22 @@ func (in *BottlerocketBootstrap) DeepCopy() *BottlerocketBootstrap { - return out - } - -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *BottlerocketBootstrapContainer) DeepCopyInto(out *BottlerocketBootstrapContainer) { -+ *out = *in -+ out.ImageMeta = in.ImageMeta -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootstrapContainer. -+func (in *BottlerocketBootstrapContainer) DeepCopy() *BottlerocketBootstrapContainer { -+ if in == nil { -+ return nil -+ } -+ out := new(BottlerocketBootstrapContainer) -+ in.DeepCopyInto(out) -+ return out -+} -+ - // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. - func (in *BottlerocketControl) DeepCopyInto(out *BottlerocketControl) { - *out = *in -@@ -217,6 +233,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { - *out = make([]BottlerocketHostContainer, len(*in)) - copy(*out, *in) - } -+ if in.BottlerocketCustomBootstrapContainers != nil { -+ in, out := &in.BottlerocketCustomBootstrapContainers, &out.BottlerocketCustomBootstrapContainers -+ *out = make([]BottlerocketBootstrapContainer, len(*in)) -+ copy(*out, *in) -+ } - } - - // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. -@@ -640,6 +661,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { - *out = make([]BottlerocketHostContainer, len(*in)) - copy(*out, *in) - } -+ if in.BottlerocketCustomBootstrapContainers != nil { -+ in, out := &in.BottlerocketCustomBootstrapContainers, &out.BottlerocketCustomBootstrapContainers -+ *out = make([]BottlerocketBootstrapContainer, len(*in)) -+ copy(*out, *in) -+ } - } - - // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -index 649b9c0bc..af15828e1 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -@@ -1267,6 +1267,48 @@ spec: - the version of the above components during upgrades. - type: string - type: object -+ bottlerocketCustomBootstrapContainers: -+ description: BottlerocketCustomBootstrapContainers adds additional -+ bootstrap containers for Bottlerocket. This is only for bottlerocket. -+ items: -+ description: BottlerocketBootstrapContainer holds the bootstrap -+ container setting for Bottlerocket -+ properties: -+ essential: -+ description: Essential decides whether or not the container -+ should fail the boot process. Bootstrap containers configured -+ with essential = true will stop the boot process if they -+ exit code is a non-zero value. Default is false. -+ type: boolean -+ imageRepository: -+ description: ImageRepository sets the container registry -+ to pull images from. if not set, the ImageRepository defined -+ in ClusterConfiguration will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for the image. -+ In case this value is set, kubeadm does not change automatically -+ the version of the above components during upgrades. -+ type: string -+ mode: -+ description: Mode represents the bootstrap container mode. -+ enum: -+ - always -+ - "off" -+ - once -+ type: string -+ name: -+ description: Name is the bootstrap container name that will -+ be given to the container in BR's `apiserver`. -+ type: string -+ userData: -+ description: UserData is the base64-encoded userdata. -+ type: string -+ required: -+ - mode -+ - name -+ type: object -+ type: array - bottlerocketCustomHostContainers: - description: BottlerocketHostContainers contains the information - of any additional images that we will deploy as host containers -@@ -2002,6 +2044,48 @@ spec: - the version of the above components during upgrades. - type: string - type: object -+ bottlerocketCustomBootstrapContainers: -+ description: BottlerocketCustomBootstrapContainers adds additional -+ bootstrap containers for Bottlerocket. This is only for bottlerocket. -+ items: -+ description: BottlerocketBootstrapContainer holds the bootstrap -+ container setting for Bottlerocket -+ properties: -+ essential: -+ description: Essential decides whether or not the container -+ should fail the boot process. Bootstrap containers configured -+ with essential = true will stop the boot process if they -+ exit code is a non-zero value. Default is false. -+ type: boolean -+ imageRepository: -+ description: ImageRepository sets the container registry -+ to pull images from. if not set, the ImageRepository defined -+ in ClusterConfiguration will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for the image. -+ In case this value is set, kubeadm does not change automatically -+ the version of the above components during upgrades. -+ type: string -+ mode: -+ description: Mode represents the bootstrap container mode. -+ enum: -+ - always -+ - "off" -+ - once -+ type: string -+ name: -+ description: Name is the bootstrap container name that will -+ be given to the container in BR's `apiserver`. -+ type: string -+ userData: -+ description: UserData is the base64-encoded userdata. -+ type: string -+ required: -+ - mode -+ - name -+ type: object -+ type: array - bottlerocketCustomHostContainers: - description: BottlerocketCustomHostContainers contains the information - of any additional images that we will deploy as host containers -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -index 21173d07f..359b978ee 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -@@ -1302,6 +1302,53 @@ spec: - components during upgrades. - type: string - type: object -+ bottlerocketCustomBootstrapContainers: -+ description: BottlerocketCustomBootstrapContainers adds -+ additional bootstrap containers for Bottlerocket. This -+ is only for bottlerocket. -+ items: -+ description: BottlerocketBootstrapContainer holds the -+ bootstrap container setting for Bottlerocket -+ properties: -+ essential: -+ description: Essential decides whether or not the -+ container should fail the boot process. Bootstrap -+ containers configured with essential = true will -+ stop the boot process if they exit code is a non-zero -+ value. Default is false. -+ type: boolean -+ imageRepository: -+ description: ImageRepository sets the container -+ registry to pull images from. if not set, the -+ ImageRepository defined in ClusterConfiguration -+ will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for -+ the image. In case this value is set, kubeadm -+ does not change automatically the version of the -+ above components during upgrades. -+ type: string -+ mode: -+ description: Mode represents the bootstrap container -+ mode. -+ enum: -+ - always -+ - "off" -+ - once -+ type: string -+ name: -+ description: Name is the bootstrap container name -+ that will be given to the container in BR's `apiserver`. -+ type: string -+ userData: -+ description: UserData is the base64-encoded userdata. -+ type: string -+ required: -+ - mode -+ - name -+ type: object -+ type: array - bottlerocketCustomHostContainers: - description: BottlerocketHostContainers contains the information - of any additional images that we will deploy as host -@@ -2087,6 +2134,53 @@ spec: - components during upgrades. - type: string - type: object -+ bottlerocketCustomBootstrapContainers: -+ description: BottlerocketCustomBootstrapContainers adds -+ additional bootstrap containers for Bottlerocket. This -+ is only for bottlerocket. -+ items: -+ description: BottlerocketBootstrapContainer holds the -+ bootstrap container setting for Bottlerocket -+ properties: -+ essential: -+ description: Essential decides whether or not the -+ container should fail the boot process. Bootstrap -+ containers configured with essential = true will -+ stop the boot process if they exit code is a non-zero -+ value. Default is false. -+ type: boolean -+ imageRepository: -+ description: ImageRepository sets the container -+ registry to pull images from. if not set, the -+ ImageRepository defined in ClusterConfiguration -+ will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for -+ the image. In case this value is set, kubeadm -+ does not change automatically the version of the -+ above components during upgrades. -+ type: string -+ mode: -+ description: Mode represents the bootstrap container -+ mode. -+ enum: -+ - always -+ - "off" -+ - once -+ type: string -+ name: -+ description: Name is the bootstrap container name -+ that will be given to the container in BR's `apiserver`. -+ type: string -+ userData: -+ description: UserData is the base64-encoded userdata. -+ type: string -+ required: -+ - mode -+ - name -+ type: object -+ type: array - bottlerocketCustomHostContainers: - description: BottlerocketCustomHostContainers contains - the information of any additional images that we will -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -index bc5094eb1..fe280e091 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -@@ -34,6 +34,26 @@ user-data = "{{.UserData}}" - {{template "hostContainerSettings" $hContainer }} - {{- end -}} - {{- end -}} -+` -+ -+ bootstrapContainerTemplate = `{{ define "bootstrapContainerSettings" -}} -+[settings.bootstrap-containers.{{.Name}}] -+essential = {{.Essential}} -+mode = "{{.Mode}}" -+{{- if (ne (imageUrl .ImageMeta) "")}} -+source = "{{imageUrl .ImageMeta}}" -+{{- end -}} -+{{- if (ne .UserData "")}} -+user-data = "{{.UserData}}" -+{{- end -}} -+{{- end -}} -+` -+ -+ bootstrapContainerSliceTemplate = `{{ define "bootstrapContainerSlice" -}} -+{{- range $bContainer := .BootstrapContainers }} -+{{template "bootstrapContainerSettings" $bContainer }} -+{{- end -}} -+{{- end -}} - ` - - networkInitTemplate = `{{ define "networkInitSettings" -}} -@@ -68,6 +88,10 @@ trusted=true - - {{template "kubernetesInitSettings" .}} - -+{{- if .BootstrapContainers}} -+{{template "bootstrapContainerSlice" .}} -+{{- end -}} -+ - {{- if (ne .HTTPSProxyEndpoint "")}} - {{template "networkInitSettings" .}} - {{- end -}} -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -new file mode 100644 -index 000000000..9065a7c58 ---- /dev/null -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -@@ -0,0 +1,99 @@ -+package bottlerocket -+ -+import ( -+ "testing" -+ -+ . "github.com/onsi/gomega" -+ -+ bootstrapv1 "sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1" -+) -+ -+const userData = ` -+[settings.host-containers.admin] -+enabled = true -+superpowered = true -+user-data = "B64USERDATA" -+[settings.host-containers.kubeadm-bootstrap] -+enabled = true -+superpowered = true -+source = "REPO:TAG" -+user-data = "B64USERDATA" -+ -+[settings.kubernetes] -+cluster-domain = "cluster.local" -+standalone-mode = true -+authentication-mode = "tls" -+server-tls-bootstrap = false -+pod-infra-container-image = "PAUSE" -+provider-id = "PROVIDERID" -+ -+[settings.bootstrap-containers.BOOTSTRAP] -+essential = false -+mode = "MODE" -+user-data = "B64USERDATA" -+[settings.network] -+https-proxy = "PROXY" -+no-proxy = [] -+[settings.container-registry.mirrors] -+"public.ecr.aws" = ["https://REGISTRYENDPOINT"] -+[settings.pki.registry-mirror-ca] -+data = "REGISTRYCA" -+trusted=true -+[settings.kubernetes.node-labels] -+KEY=VAR -+[settings.kubernetes.node-taints] -+KEY=VAR` -+ -+func TestGenerateUserData(t *testing.T) { -+ g := NewWithT(t) -+ -+ testcases := []struct { -+ name string -+ input *BottlerocketSettingsInput -+ output string -+ }{ -+ { -+ name: "full settings", -+ input: &BottlerocketSettingsInput{ -+ PauseContainerSource: "PAUSE", -+ HTTPSProxyEndpoint: "PROXY", -+ RegistryMirrorEndpoint: "REGISTRYENDPOINT", -+ RegistryMirrorCACert: "REGISTRYCA", -+ NodeLabels: "KEY=VAR", -+ Taints: "KEY=VAR", -+ ProviderId: "PROVIDERID", -+ HostContainers: []bootstrapv1.BottlerocketHostContainer{ -+ { -+ Name: "admin", -+ Superpowered: true, -+ UserData: "B64USERDATA", -+ }, -+ { -+ Name: "kubeadm-bootstrap", -+ Superpowered: true, -+ ImageMeta: bootstrapv1.ImageMeta{ -+ ImageRepository: "REPO", -+ ImageTag: "TAG", -+ }, -+ UserData: "B64USERDATA", -+ }, -+ }, -+ BootstrapContainers: []bootstrapv1.BottlerocketBootstrapContainer{ -+ { -+ Name: "BOOTSTRAP", -+ Mode: "MODE", -+ UserData: "B64USERDATA", -+ }, -+ }, -+ }, -+ output: userData, -+ }, -+ } -+ for _, testcase := range testcases { -+ t.Run(testcase.name, func(t *testing.T) { -+ b, err := generateNodeUserData("TestBottlerocketInit", bottlerocketNodeInitSettingsTemplate, testcase.input) -+ g.Expect(err).NotTo(HaveOccurred()) -+ g.Expect(string(b)).To(Equal(testcase.output)) -+ }) -+ } -+} -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -index 0e6124b4c..e504684a0 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -@@ -23,14 +23,15 @@ const ( - ) - - type BottlerocketConfig struct { -- Pause bootstrapv1.Pause -- BottlerocketBootstrap bootstrapv1.BottlerocketBootstrap -- BottlerocketControl bootstrapv1.BottlerocketControl -- ProxyConfiguration bootstrapv1.ProxyConfiguration -- RegistryMirrorConfiguration bootstrapv1.RegistryMirrorConfiguration -- KubeletExtraArgs map[string]string -- Taints []corev1.Taint -- BottlerocketCustomHostContainers []bootstrapv1.BottlerocketHostContainer -+ Pause bootstrapv1.Pause -+ BottlerocketBootstrap bootstrapv1.BottlerocketBootstrap -+ BottlerocketControl bootstrapv1.BottlerocketControl -+ ProxyConfiguration bootstrapv1.ProxyConfiguration -+ RegistryMirrorConfiguration bootstrapv1.RegistryMirrorConfiguration -+ KubeletExtraArgs map[string]string -+ Taints []corev1.Taint -+ BottlerocketCustomHostContainers []bootstrapv1.BottlerocketHostContainer -+ BottlerocketCustomBootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer - } - - type BottlerocketSettingsInput struct { -@@ -43,6 +44,7 @@ type BottlerocketSettingsInput struct { - Taints string - ProviderId string - HostContainers []bootstrapv1.BottlerocketHostContainer -+ BootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer - } - - type HostPath struct { -@@ -103,6 +105,12 @@ func generateNodeUserData(kind string, tpl string, data interface{}) ([]byte, er - if _, err := tm.Parse(hostContainerSliceTemplate); err != nil { - return nil, errors.Wrapf(err, "failed to parse hostContainerSettingsSlice %s template", kind) - } -+ if _, err := tm.Parse(bootstrapContainerTemplate); err != nil { -+ return nil, errors.Wrapf(err, "failed to parse bootstrapContainerSettings %s template", kind) -+ } -+ if _, err := tm.Parse(bootstrapContainerSliceTemplate); err != nil { -+ return nil, errors.Wrapf(err, "failed to parse bootstrapContainerSettingsSlice %s template", kind) -+ } - if _, err := tm.Parse(kubernetesInitTemplate); err != nil { - return nil, errors.Wrapf(err, "failed to parse kubernetes %s template", kind) - } -@@ -179,9 +187,10 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot - HTTPSProxyEndpoint: config.ProxyConfiguration.HTTPSProxy, - RegistryMirrorEndpoint: config.RegistryMirrorConfiguration.Endpoint, - NodeLabels: parseNodeLabels(config.KubeletExtraArgs["node-labels"]), // empty string if it does not exist -- Taints: parseTaints(config.Taints), //empty string if it does not exist -+ Taints: parseTaints(config.Taints), // empty string if it does not exist - ProviderId: config.KubeletExtraArgs["provider-id"], - HostContainers: hostContainers, -+ BootstrapContainers: config.BottlerocketCustomBootstrapContainers, - } - - if len(config.ProxyConfiguration.NoProxy) > 0 { -diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -index 8eb1d6c02..7cc63012c 100644 ---- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -+++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -@@ -473,10 +473,11 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex - } - - bottlerocketConfig = &bottlerocket.BottlerocketConfig{ -- Pause: scope.Config.Spec.ClusterConfiguration.Pause, -- BottlerocketBootstrap: scope.Config.Spec.ClusterConfiguration.BottlerocketBootstrap, -- BottlerocketControl: scope.Config.Spec.ClusterConfiguration.BottlerocketControl, -- BottlerocketCustomHostContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketHostContainers, -+ Pause: scope.Config.Spec.ClusterConfiguration.Pause, -+ BottlerocketBootstrap: scope.Config.Spec.ClusterConfiguration.BottlerocketBootstrap, -+ BottlerocketControl: scope.Config.Spec.ClusterConfiguration.BottlerocketControl, -+ BottlerocketCustomHostContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketHostContainers, -+ BottlerocketCustomBootstrapContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketCustomBootstrapContainers, - } - if scope.Config.Spec.ClusterConfiguration.Proxy.HTTPSProxy != "" { - bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.ClusterConfiguration.Proxy -@@ -679,10 +680,11 @@ func (r *KubeadmConfigReconciler) joinWorker(ctx context.Context, scope *Scope) - }) - case bootstrapv1.Bottlerocket: - bottlerocketConfig := &bottlerocket.BottlerocketConfig{ -- Pause: scope.Config.Spec.JoinConfiguration.Pause, -- BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, -- BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, -- BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, -+ Pause: scope.Config.Spec.JoinConfiguration.Pause, -+ BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, -+ BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, -+ BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, -+ BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, - } - if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { - bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy -@@ -807,10 +809,11 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S - }) - case bootstrapv1.Bottlerocket: - bottlerocketConfig := &bottlerocket.BottlerocketConfig{ -- Pause: scope.Config.Spec.JoinConfiguration.Pause, -- BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, -- BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, -- BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, -+ Pause: scope.Config.Spec.JoinConfiguration.Pause, -+ BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, -+ BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, -+ BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, -+ BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, - } - if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { - bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy -diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -index 6b4eac17b..2e3bc99ea 100644 ---- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -@@ -562,6 +562,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta2_ClusterConfigur - out.FeatureGates = *(*map[string]bool)(unsafe.Pointer(&in.FeatureGates)) - out.ClusterName = in.ClusterName - // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type -+ // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - return nil - } - -@@ -871,6 +872,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta2_JoinConfiguration( - // WARNING: in.SkipPhases requires manual conversion: does not exist in peer-type - // WARNING: in.Patches requires manual conversion: does not exist in peer-type - // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type -+ // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - return nil - } - -diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -index d290e4d94..1b2d94a1d 100644 ---- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -@@ -566,6 +566,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta3_ClusterConfigur - out.FeatureGates = *(*map[string]bool)(unsafe.Pointer(&in.FeatureGates)) - out.ClusterName = in.ClusterName - // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type -+ // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - return nil - } - -@@ -863,6 +864,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta3_JoinConfiguration( - out.SkipPhases = *(*[]string)(unsafe.Pointer(&in.SkipPhases)) - out.Patches = (*Patches)(unsafe.Pointer(in.Patches)) - // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type -+ // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - return nil - } - -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -index b3d5958dc..4ac7c44e0 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -@@ -1547,6 +1547,52 @@ spec: - upgrades. - type: string - type: object -+ bottlerocketCustomBootstrapContainers: -+ description: BottlerocketCustomBootstrapContainers adds additional -+ bootstrap containers for Bottlerocket. This is only for -+ bottlerocket. -+ items: -+ description: BottlerocketBootstrapContainer holds the bootstrap -+ container setting for Bottlerocket -+ properties: -+ essential: -+ description: Essential decides whether or not the container -+ should fail the boot process. Bootstrap containers -+ configured with essential = true will stop the boot -+ process if they exit code is a non-zero value. Default -+ is false. -+ type: boolean -+ imageRepository: -+ description: ImageRepository sets the container registry -+ to pull images from. if not set, the ImageRepository -+ defined in ClusterConfiguration will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for the -+ image. In case this value is set, kubeadm does not -+ change automatically the version of the above components -+ during upgrades. -+ type: string -+ mode: -+ description: Mode represents the bootstrap container -+ mode. -+ enum: -+ - always -+ - "off" -+ - once -+ type: string -+ name: -+ description: Name is the bootstrap container name that -+ will be given to the container in BR's `apiserver`. -+ type: string -+ userData: -+ description: UserData is the base64-encoded userdata. -+ type: string -+ required: -+ - mode -+ - name -+ type: object -+ type: array - bottlerocketCustomHostContainers: - description: BottlerocketHostContainers contains the information - of any additional images that we will deploy as host containers -@@ -2312,6 +2358,52 @@ spec: - upgrades. - type: string - type: object -+ bottlerocketCustomBootstrapContainers: -+ description: BottlerocketCustomBootstrapContainers adds additional -+ bootstrap containers for Bottlerocket. This is only for -+ bottlerocket. -+ items: -+ description: BottlerocketBootstrapContainer holds the bootstrap -+ container setting for Bottlerocket -+ properties: -+ essential: -+ description: Essential decides whether or not the container -+ should fail the boot process. Bootstrap containers -+ configured with essential = true will stop the boot -+ process if they exit code is a non-zero value. Default -+ is false. -+ type: boolean -+ imageRepository: -+ description: ImageRepository sets the container registry -+ to pull images from. if not set, the ImageRepository -+ defined in ClusterConfiguration will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for the -+ image. In case this value is set, kubeadm does not -+ change automatically the version of the above components -+ during upgrades. -+ type: string -+ mode: -+ description: Mode represents the bootstrap container -+ mode. -+ enum: -+ - always -+ - "off" -+ - once -+ type: string -+ name: -+ description: Name is the bootstrap container name that -+ will be given to the container in BR's `apiserver`. -+ type: string -+ userData: -+ description: UserData is the base64-encoded userdata. -+ type: string -+ required: -+ - mode -+ - name -+ type: object -+ type: array - bottlerocketCustomHostContainers: - description: BottlerocketCustomHostContainers contains the - information of any additional images that we will deploy -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -index a9d34477b..ec979a04f 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -@@ -1503,6 +1503,56 @@ spec: - the above components during upgrades. - type: string - type: object -+ bottlerocketCustomBootstrapContainers: -+ description: BottlerocketCustomBootstrapContainers -+ adds additional bootstrap containers for Bottlerocket. -+ This is only for bottlerocket. -+ items: -+ description: BottlerocketBootstrapContainer holds -+ the bootstrap container setting for Bottlerocket -+ properties: -+ essential: -+ description: Essential decides whether or not -+ the container should fail the boot process. -+ Bootstrap containers configured with essential -+ = true will stop the boot process if they -+ exit code is a non-zero value. Default is -+ false. -+ type: boolean -+ imageRepository: -+ description: ImageRepository sets the container -+ registry to pull images from. if not set, -+ the ImageRepository defined in ClusterConfiguration -+ will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag -+ for the image. In case this value is set, -+ kubeadm does not change automatically the -+ version of the above components during upgrades. -+ type: string -+ mode: -+ description: Mode represents the bootstrap container -+ mode. -+ enum: -+ - always -+ - "off" -+ - once -+ type: string -+ name: -+ description: Name is the bootstrap container -+ name that will be given to the container in -+ BR's `apiserver`. -+ type: string -+ userData: -+ description: UserData is the base64-encoded -+ userdata. -+ type: string -+ required: -+ - mode -+ - name -+ type: object -+ type: array - bottlerocketCustomHostContainers: - description: BottlerocketHostContainers contains the - information of any additional images that we will -@@ -2320,6 +2370,56 @@ spec: - the above components during upgrades. - type: string - type: object -+ bottlerocketCustomBootstrapContainers: -+ description: BottlerocketCustomBootstrapContainers -+ adds additional bootstrap containers for Bottlerocket. -+ This is only for bottlerocket. -+ items: -+ description: BottlerocketBootstrapContainer holds -+ the bootstrap container setting for Bottlerocket -+ properties: -+ essential: -+ description: Essential decides whether or not -+ the container should fail the boot process. -+ Bootstrap containers configured with essential -+ = true will stop the boot process if they -+ exit code is a non-zero value. Default is -+ false. -+ type: boolean -+ imageRepository: -+ description: ImageRepository sets the container -+ registry to pull images from. if not set, -+ the ImageRepository defined in ClusterConfiguration -+ will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag -+ for the image. In case this value is set, -+ kubeadm does not change automatically the -+ version of the above components during upgrades. -+ type: string -+ mode: -+ description: Mode represents the bootstrap container -+ mode. -+ enum: -+ - always -+ - "off" -+ - once -+ type: string -+ name: -+ description: Name is the bootstrap container -+ name that will be given to the container in -+ BR's `apiserver`. -+ type: string -+ userData: -+ description: UserData is the base64-encoded -+ userdata. -+ type: string -+ required: -+ - mode -+ - name -+ type: object -+ type: array - bottlerocketCustomHostContainers: - description: BottlerocketCustomHostContainers contains - the information of any additional images that we --- -2.39.3 (Apple Git-145) - diff --git a/projects/kubernetes-sigs/cluster-api/patches/0022-Make-bottlerocket-admin-control-custom-bootstrap-con.patch b/projects/kubernetes-sigs/cluster-api/patches/0020-Make-bottlerocket-admin-control-custom-bootstrap-con.patch similarity index 97% rename from projects/kubernetes-sigs/cluster-api/patches/0022-Make-bottlerocket-admin-control-custom-bootstrap-con.patch rename to projects/kubernetes-sigs/cluster-api/patches/0020-Make-bottlerocket-admin-control-custom-bootstrap-con.patch index 3bbc1acfcc..3a2e022369 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0022-Make-bottlerocket-admin-control-custom-bootstrap-con.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0020-Make-bottlerocket-admin-control-custom-bootstrap-con.patch @@ -1,7 +1,7 @@ -From 7c58664fcf657c96a4b64b61daa0c022588627bf Mon Sep 17 00:00:00 2001 +From 1a30bcd6ee3a114754750e8ecef7e98959588602 Mon Sep 17 00:00:00 2001 From: Jiayi Wang Date: Thu, 5 Jan 2023 14:56:09 -0500 -Subject: [PATCH 22/40] Make bottlerocket admin, control, custom bootstrap +Subject: [PATCH 20/40] Make bottlerocket admin, control, custom bootstrap container images updatable in webhook --- @@ -113,5 +113,5 @@ index 275f2cb12..0fb9025d1 100644 for _, tt := range tests { -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0023-Mark-etcd-machine-status-to-running-after-etcd-contr.patch b/projects/kubernetes-sigs/cluster-api/patches/0021-Mark-etcd-machine-status-to-running-after-etcd-contr.patch similarity index 89% rename from projects/kubernetes-sigs/cluster-api/patches/0023-Mark-etcd-machine-status-to-running-after-etcd-contr.patch rename to projects/kubernetes-sigs/cluster-api/patches/0021-Mark-etcd-machine-status-to-running-after-etcd-contr.patch index 478338daf8..7c716c71c3 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0023-Mark-etcd-machine-status-to-running-after-etcd-contr.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0021-Mark-etcd-machine-status-to-running-after-etcd-contr.patch @@ -1,7 +1,7 @@ -From 0ca43a175d36d21f8b90ab2e5b3694d802c34854 Mon Sep 17 00:00:00 2001 +From 613a7e58f0ae851a40607568b7091ad75d37e6c9 Mon Sep 17 00:00:00 2001 From: Jiayi Wang Date: Mon, 9 Jan 2023 15:41:05 -0500 -Subject: [PATCH 23/40] Mark etcd machine status to running after etcd +Subject: [PATCH 21/40] Mark etcd machine status to running after etcd controller adds the etcd machine ready label --- @@ -28,10 +28,10 @@ index 07395019e..30c29647c 100644 ExcludeNodeDrainingAnnotation = "machine.cluster.x-k8s.io/exclude-node-draining" diff --git a/internal/controllers/machine/machine_controller_phases.go b/internal/controllers/machine/machine_controller_phases.go -index 9b251469e..e17031c99 100644 +index 41382bbaf..16febdda8 100644 --- a/internal/controllers/machine/machine_controller_phases.go +++ b/internal/controllers/machine/machine_controller_phases.go -@@ -72,8 +72,7 @@ func (r *Reconciler) reconcilePhase(_ context.Context, m *clusterv1.Machine) { +@@ -70,8 +70,7 @@ func (r *Reconciler) reconcilePhase(_ context.Context, m *clusterv1.Machine) { } if _, ok := m.Labels[clusterv1.MachineEtcdClusterLabelName]; ok { @@ -42,5 +42,5 @@ index 9b251469e..e17031c99 100644 } } -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0021-Support-configuring-bottlerocket-admin-container-ima.patch b/projects/kubernetes-sigs/cluster-api/patches/0021-Support-configuring-bottlerocket-admin-container-ima.patch deleted file mode 100644 index a38f86fb71..0000000000 --- a/projects/kubernetes-sigs/cluster-api/patches/0021-Support-configuring-bottlerocket-admin-container-ima.patch +++ /dev/null @@ -1,523 +0,0 @@ -From 5e2e477b86dd4269ef96a4ee0bcfa1f9cc58d20f Mon Sep 17 00:00:00 2001 -From: Jiayi Wang -Date: Wed, 23 Nov 2022 09:26:28 -0500 -Subject: [PATCH 21/40] Support configuring bottlerocket admin container image - ---- - .../api/v1alpha4/zz_generated.conversion.go | 2 + - .../kubeadm/api/v1beta1/kubeadm_types.go | 17 ++++ - .../api/v1beta1/zz_generated.deepcopy.go | 18 ++++ - ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 30 +++++++ - ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 32 ++++++++ - .../internal/bottlerocket/bootstrap_test.go | 82 ++++++++++++++++++- - .../internal/bottlerocket/bottlerocket.go | 2 + - .../controllers/kubeadmconfig_controller.go | 3 + - .../zz_generated.conversion.go | 2 + - .../zz_generated.conversion.go | 2 + - ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 32 ++++++++ - ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 34 ++++++++ - 12 files changed, 254 insertions(+), 2 deletions(-) - -diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -index de8032f59..7af108f9e 100644 ---- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -@@ -694,6 +694,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(i - if err := Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { - return err - } -+ // WARNING: in.BottlerocketAdmin requires manual conversion: does not exist in peer-type - if err := Convert_v1beta1_BottlerocketControl_To_v1alpha4_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { - return err - } -@@ -1114,6 +1115,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1b - if err := Convert_v1beta1_BottlerocketBootstrap_To_v1alpha4_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { - return err - } -+ // WARNING: in.BottlerocketAdmin requires manual conversion: does not exist in peer-type - if err := Convert_v1beta1_BottlerocketControl_To_v1alpha4_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { - return err - } -diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -index 48e5f4b8e..409d724b3 100644 ---- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -+++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -@@ -83,6 +83,11 @@ type ClusterConfiguration struct { - // +optional - BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` - -+ // BottlerocketAdmin holds the image source for admin container -+ // This is only for bottlerocket -+ // +optional -+ BottlerocketAdmin BottlerocketAdmin `json:"bottlerocketAdmin,omitempty"` -+ - // BottlerocketControl holds the image source for control container - // This is only for bottlerocket - // +optional -@@ -196,6 +201,13 @@ type BottlerocketBootstrap struct { - ImageMeta `json:",inline"` - } - -+// BottlerocketAdmin holds the settings of admin container for bottlerocket nodes -+// This setting is ONLY for bottlerocket nodes. -+type BottlerocketAdmin struct { -+ // ImageMeta allows to customize the image used for the BottlerocketAdmin component -+ ImageMeta `json:",inline"` -+} -+ - // BottlerocketControl holds the settings of control container for bottlerocket nodes - // This setting is ONLY for bottlerocket nodes. - type BottlerocketControl struct { -@@ -498,6 +510,11 @@ type JoinConfiguration struct { - // +optional - BottlerocketBootstrap BottlerocketBootstrap `json:"bottlerocketBootstrap,omitempty"` - -+ // BottlerocketAdmin holds the image source for admin container -+ // This is only for bottlerocket -+ // +optional -+ BottlerocketAdmin BottlerocketAdmin `json:"bottlerocketAdmin,omitempty"` -+ - // BottlerocketControl holds the image source for control container - // This is only for bottlerocket - // +optional -diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -index 64e4eeff7..ca5525885 100644 ---- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -+++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -@@ -142,6 +142,22 @@ func (in *BootstrapTokenString) DeepCopy() *BootstrapTokenString { - return out - } - -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *BottlerocketAdmin) DeepCopyInto(out *BottlerocketAdmin) { -+ *out = *in -+ out.ImageMeta = in.ImageMeta -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketAdmin. -+func (in *BottlerocketAdmin) DeepCopy() *BottlerocketAdmin { -+ if in == nil { -+ return nil -+ } -+ out := new(BottlerocketAdmin) -+ in.DeepCopyInto(out) -+ return out -+} -+ - // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. - func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { - *out = *in -@@ -212,6 +228,7 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { - out.TypeMeta = in.TypeMeta - out.Pause = in.Pause - out.BottlerocketBootstrap = in.BottlerocketBootstrap -+ out.BottlerocketAdmin = in.BottlerocketAdmin - out.BottlerocketControl = in.BottlerocketControl - in.Proxy.DeepCopyInto(&out.Proxy) - out.RegistryMirror = in.RegistryMirror -@@ -636,6 +653,7 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { - out.TypeMeta = in.TypeMeta - out.Pause = in.Pause - out.BottlerocketBootstrap = in.BottlerocketBootstrap -+ out.BottlerocketAdmin = in.BottlerocketAdmin - out.BottlerocketControl = in.BottlerocketControl - in.Proxy.DeepCopyInto(&out.Proxy) - out.RegistryMirror = in.RegistryMirror -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -index af15828e1..78973aca9 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -@@ -1237,6 +1237,21 @@ spec: - schemas to the latest internal value, and may reject unrecognized - values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string -+ bottlerocketAdmin: -+ description: BottlerocketAdmin holds the image source for admin -+ container This is only for bottlerocket -+ properties: -+ imageRepository: -+ description: ImageRepository sets the container registry to -+ pull images from. if not set, the ImageRepository defined -+ in ClusterConfiguration will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for the image. -+ In case this value is set, kubeadm does not change automatically -+ the version of the above components during upgrades. -+ type: string -+ type: object - bottlerocketBootstrap: - description: BottlerocketBootstrap holds the image source for - kubeadm bootstrap container This is only for bottlerocket -@@ -2014,6 +2029,21 @@ spec: - schemas to the latest internal value, and may reject unrecognized - values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string -+ bottlerocketAdmin: -+ description: BottlerocketAdmin holds the image source for admin -+ container This is only for bottlerocket -+ properties: -+ imageRepository: -+ description: ImageRepository sets the container registry to -+ pull images from. if not set, the ImageRepository defined -+ in ClusterConfiguration will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for the image. -+ In case this value is set, kubeadm does not change automatically -+ the version of the above components during upgrades. -+ type: string -+ type: object - bottlerocketBootstrap: - description: BottlerocketBootstrap holds the image source for - kubeadm bootstrap container This is only for bottlerocket -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -index 359b978ee..99af465e7 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -@@ -1270,6 +1270,22 @@ spec: - convert recognized schemas to the latest internal value, - and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string -+ bottlerocketAdmin: -+ description: BottlerocketAdmin holds the image source -+ for admin container This is only for bottlerocket -+ properties: -+ imageRepository: -+ description: ImageRepository sets the container registry -+ to pull images from. if not set, the ImageRepository -+ defined in ClusterConfiguration will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for -+ the image. In case this value is set, kubeadm does -+ not change automatically the version of the above -+ components during upgrades. -+ type: string -+ type: object - bottlerocketBootstrap: - description: BottlerocketBootstrap holds the image source - for kubeadm bootstrap container This is only for bottlerocket -@@ -2102,6 +2118,22 @@ spec: - convert recognized schemas to the latest internal value, - and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string -+ bottlerocketAdmin: -+ description: BottlerocketAdmin holds the image source -+ for admin container This is only for bottlerocket -+ properties: -+ imageRepository: -+ description: ImageRepository sets the container registry -+ to pull images from. if not set, the ImageRepository -+ defined in ClusterConfiguration will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for -+ the image. In case this value is set, kubeadm does -+ not change automatically the version of the above -+ components during upgrades. -+ type: string -+ type: object - bottlerocketBootstrap: - description: BottlerocketBootstrap holds the image source - for kubeadm bootstrap container This is only for bottlerocket -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -index 9065a7c58..5ee1b0d45 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -@@ -8,7 +8,44 @@ import ( - bootstrapv1 "sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1" - ) - --const userData = ` -+const userDataFullSetting = ` -+[settings.host-containers.admin] -+enabled = true -+superpowered = true -+source = "REPO:TAG" -+user-data = "B64USERDATA" -+[settings.host-containers.kubeadm-bootstrap] -+enabled = true -+superpowered = true -+source = "REPO:TAG" -+user-data = "B64USERDATA" -+ -+[settings.kubernetes] -+cluster-domain = "cluster.local" -+standalone-mode = true -+authentication-mode = "tls" -+server-tls-bootstrap = false -+pod-infra-container-image = "PAUSE" -+provider-id = "PROVIDERID" -+ -+[settings.bootstrap-containers.BOOTSTRAP] -+essential = false -+mode = "MODE" -+user-data = "B64USERDATA" -+[settings.network] -+https-proxy = "PROXY" -+no-proxy = [] -+[settings.container-registry.mirrors] -+"public.ecr.aws" = ["https://REGISTRYENDPOINT"] -+[settings.pki.registry-mirror-ca] -+data = "REGISTRYCA" -+trusted=true -+[settings.kubernetes.node-labels] -+KEY=VAR -+[settings.kubernetes.node-taints] -+KEY=VAR` -+ -+const userDataNoAdminImage = ` - [settings.host-containers.admin] - enabled = true - superpowered = true -@@ -66,6 +103,47 @@ func TestGenerateUserData(t *testing.T) { - { - Name: "admin", - Superpowered: true, -+ ImageMeta: bootstrapv1.ImageMeta{ -+ ImageRepository: "REPO", -+ ImageTag: "TAG", -+ }, -+ UserData: "B64USERDATA", -+ }, -+ { -+ Name: "kubeadm-bootstrap", -+ Superpowered: true, -+ ImageMeta: bootstrapv1.ImageMeta{ -+ ImageRepository: "REPO", -+ ImageTag: "TAG", -+ }, -+ UserData: "B64USERDATA", -+ }, -+ }, -+ BootstrapContainers: []bootstrapv1.BottlerocketBootstrapContainer{ -+ { -+ Name: "BOOTSTRAP", -+ Mode: "MODE", -+ UserData: "B64USERDATA", -+ }, -+ }, -+ }, -+ output: userDataFullSetting, -+ }, -+ { -+ name: "no admin image meta", -+ input: &BottlerocketSettingsInput{ -+ PauseContainerSource: "PAUSE", -+ HTTPSProxyEndpoint: "PROXY", -+ RegistryMirrorEndpoint: "REGISTRYENDPOINT", -+ RegistryMirrorCACert: "REGISTRYCA", -+ NodeLabels: "KEY=VAR", -+ Taints: "KEY=VAR", -+ ProviderId: "PROVIDERID", -+ HostContainers: []bootstrapv1.BottlerocketHostContainer{ -+ { -+ Name: "admin", -+ Superpowered: true, -+ ImageMeta: bootstrapv1.ImageMeta{}, - UserData: "B64USERDATA", - }, - { -@@ -86,7 +164,7 @@ func TestGenerateUserData(t *testing.T) { - }, - }, - }, -- output: userData, -+ output: userDataNoAdminImage, - }, - } - for _, testcase := range testcases { -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -index e504684a0..9848f47e8 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -@@ -25,6 +25,7 @@ const ( - type BottlerocketConfig struct { - Pause bootstrapv1.Pause - BottlerocketBootstrap bootstrapv1.BottlerocketBootstrap -+ BottlerocketAdmin bootstrapv1.BottlerocketAdmin - BottlerocketControl bootstrapv1.BottlerocketControl - ProxyConfiguration bootstrapv1.ProxyConfiguration - RegistryMirrorConfiguration bootstrapv1.RegistryMirrorConfiguration -@@ -160,6 +161,7 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot - { - Name: "admin", - Superpowered: true, -+ ImageMeta: config.BottlerocketAdmin.ImageMeta, - UserData: b64AdminContainerUserData, - }, - { -diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -index 7cc63012c..f4f3624c4 100644 ---- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -+++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -@@ -475,6 +475,7 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex - bottlerocketConfig = &bottlerocket.BottlerocketConfig{ - Pause: scope.Config.Spec.ClusterConfiguration.Pause, - BottlerocketBootstrap: scope.Config.Spec.ClusterConfiguration.BottlerocketBootstrap, -+ BottlerocketAdmin: scope.Config.Spec.ClusterConfiguration.BottlerocketAdmin, - BottlerocketControl: scope.Config.Spec.ClusterConfiguration.BottlerocketControl, - BottlerocketCustomHostContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketHostContainers, - BottlerocketCustomBootstrapContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketCustomBootstrapContainers, -@@ -682,6 +683,7 @@ func (r *KubeadmConfigReconciler) joinWorker(ctx context.Context, scope *Scope) - bottlerocketConfig := &bottlerocket.BottlerocketConfig{ - Pause: scope.Config.Spec.JoinConfiguration.Pause, - BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, -+ BottlerocketAdmin: scope.Config.Spec.JoinConfiguration.BottlerocketAdmin, - BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, - BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, - BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, -@@ -811,6 +813,7 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S - bottlerocketConfig := &bottlerocket.BottlerocketConfig{ - Pause: scope.Config.Spec.JoinConfiguration.Pause, - BottlerocketBootstrap: scope.Config.Spec.JoinConfiguration.BottlerocketBootstrap, -+ BottlerocketAdmin: scope.Config.Spec.JoinConfiguration.BottlerocketAdmin, - BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, - BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, - BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, -diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -index 2e3bc99ea..8b6475592 100644 ---- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -@@ -528,6 +528,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta2_ClusterConfigur - if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { - return err - } -+ // WARNING: in.BottlerocketAdmin requires manual conversion: does not exist in peer-type - if err := Convert_v1beta1_BottlerocketControl_To_upstreamv1beta2_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { - return err - } -@@ -844,6 +845,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta2_JoinConfiguration( - if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta2_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { - return err - } -+ // WARNING: in.BottlerocketAdmin requires manual conversion: does not exist in peer-type - if err := Convert_v1beta1_BottlerocketControl_To_upstreamv1beta2_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { - return err - } -diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -index 1b2d94a1d..4584e6266 100644 ---- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -@@ -532,6 +532,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta3_ClusterConfigur - if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { - return err - } -+ // WARNING: in.BottlerocketAdmin requires manual conversion: does not exist in peer-type - if err := Convert_v1beta1_BottlerocketControl_To_upstreamv1beta3_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { - return err - } -@@ -836,6 +837,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta3_JoinConfiguration( - if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta3_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { - return err - } -+ // WARNING: in.BottlerocketAdmin requires manual conversion: does not exist in peer-type - if err := Convert_v1beta1_BottlerocketControl_To_upstreamv1beta3_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { - return err - } -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -index 4ac7c44e0..e0aaa6532 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -@@ -1515,6 +1515,22 @@ spec: - schemas to the latest internal value, and may reject unrecognized - values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string -+ bottlerocketAdmin: -+ description: BottlerocketAdmin holds the image source for -+ admin container This is only for bottlerocket -+ properties: -+ imageRepository: -+ description: ImageRepository sets the container registry -+ to pull images from. if not set, the ImageRepository -+ defined in ClusterConfiguration will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for the -+ image. In case this value is set, kubeadm does not change -+ automatically the version of the above components during -+ upgrades. -+ type: string -+ type: object - bottlerocketBootstrap: - description: BottlerocketBootstrap holds the image source - for kubeadm bootstrap container This is only for bottlerocket -@@ -2326,6 +2342,22 @@ spec: - schemas to the latest internal value, and may reject unrecognized - values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string -+ bottlerocketAdmin: -+ description: BottlerocketAdmin holds the image source for -+ admin container This is only for bottlerocket -+ properties: -+ imageRepository: -+ description: ImageRepository sets the container registry -+ to pull images from. if not set, the ImageRepository -+ defined in ClusterConfiguration will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag for the -+ image. In case this value is set, kubeadm does not change -+ automatically the version of the above components during -+ upgrades. -+ type: string -+ type: object - bottlerocketBootstrap: - description: BottlerocketBootstrap holds the image source - for kubeadm bootstrap container This is only for bottlerocket -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -index ec979a04f..e7647e47a 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -@@ -1468,6 +1468,23 @@ spec: - value, and may reject unrecognized values. More - info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string -+ bottlerocketAdmin: -+ description: BottlerocketAdmin holds the image source -+ for admin container This is only for bottlerocket -+ properties: -+ imageRepository: -+ description: ImageRepository sets the container -+ registry to pull images from. if not set, the -+ ImageRepository defined in ClusterConfiguration -+ will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag -+ for the image. In case this value is set, kubeadm -+ does not change automatically the version of -+ the above components during upgrades. -+ type: string -+ type: object - bottlerocketBootstrap: - description: BottlerocketBootstrap holds the image - source for kubeadm bootstrap container This is only -@@ -2335,6 +2352,23 @@ spec: - value, and may reject unrecognized values. More - info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string -+ bottlerocketAdmin: -+ description: BottlerocketAdmin holds the image source -+ for admin container This is only for bottlerocket -+ properties: -+ imageRepository: -+ description: ImageRepository sets the container -+ registry to pull images from. if not set, the -+ ImageRepository defined in ClusterConfiguration -+ will be used instead. -+ type: string -+ imageTag: -+ description: ImageTag allows to specify a tag -+ for the image. In case this value is set, kubeadm -+ does not change automatically the version of -+ the above components during upgrades. -+ type: string -+ type: object - bottlerocketBootstrap: - description: BottlerocketBootstrap holds the image - source for kubeadm bootstrap container This is only --- -2.39.3 (Apple Git-145) - diff --git a/projects/kubernetes-sigs/cluster-api/patches/0024-add-support-for-registry-credentials.patch b/projects/kubernetes-sigs/cluster-api/patches/0022-add-support-for-registry-credentials.patch similarity index 98% rename from projects/kubernetes-sigs/cluster-api/patches/0024-add-support-for-registry-credentials.patch rename to projects/kubernetes-sigs/cluster-api/patches/0022-add-support-for-registry-credentials.patch index 28bb792a94..520489b4ad 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0024-add-support-for-registry-credentials.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0022-add-support-for-registry-credentials.patch @@ -1,7 +1,7 @@ -From 429e9414892f385f9ff26a48bb1ee0274269a973 Mon Sep 17 00:00:00 2001 +From bd865ca607bc55d77950aa7319d3e6d97d878893 Mon Sep 17 00:00:00 2001 From: Ahree Hong Date: Wed, 14 Dec 2022 12:47:42 -0800 -Subject: [PATCH 24/40] add support for registry credentials +Subject: [PATCH 22/40] add support for registry credentials Signed-off-by: Ahree Hong --- @@ -223,5 +223,5 @@ index 043764325..17abd5d70 100644 // Purpose is the name to append to the secret generated for a cluster. -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0025-Add-support-for-configuring-NTP-servers-on-bottleroc.patch b/projects/kubernetes-sigs/cluster-api/patches/0023-Add-support-for-configuring-NTP-servers-on-bottleroc.patch similarity index 97% rename from projects/kubernetes-sigs/cluster-api/patches/0025-Add-support-for-configuring-NTP-servers-on-bottleroc.patch rename to projects/kubernetes-sigs/cluster-api/patches/0023-Add-support-for-configuring-NTP-servers-on-bottleroc.patch index 298ae70a60..ebb067bf34 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0025-Add-support-for-configuring-NTP-servers-on-bottleroc.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0023-Add-support-for-configuring-NTP-servers-on-bottleroc.patch @@ -1,7 +1,7 @@ -From 6b3b5a0a9f3a2443ccf4f57e2b3954cca5fb6c4d Mon Sep 17 00:00:00 2001 +From d1fccd9530ab23cea8bf106f92a4ff7fd9f19555 Mon Sep 17 00:00:00 2001 From: Abhinav Date: Wed, 1 Feb 2023 16:34:23 -0800 -Subject: [PATCH 25/40] Add support for configuring NTP servers on bottlerocket +Subject: [PATCH 23/40] Add support for configuring NTP servers on bottlerocket through CAPI Signed-off-by: Abhinav @@ -172,5 +172,5 @@ index 6018d66ea..83be3a157 100644 if err != nil { scope.Error(err, "Failed to generate cloud init for bottlerocket bootstrap control plane") -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0026-set-hostname-for-BR-nodes.patch b/projects/kubernetes-sigs/cluster-api/patches/0024-set-hostname-for-BR-nodes.patch similarity index 98% rename from projects/kubernetes-sigs/cluster-api/patches/0026-set-hostname-for-BR-nodes.patch rename to projects/kubernetes-sigs/cluster-api/patches/0024-set-hostname-for-BR-nodes.patch index 17555570da..8538c3f368 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0026-set-hostname-for-BR-nodes.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0024-set-hostname-for-BR-nodes.patch @@ -1,7 +1,7 @@ -From e79445462e471b135722e25dad70191fbccfc866 Mon Sep 17 00:00:00 2001 +From 4b777c2b2dca545ca36134bc06101afef51901fa Mon Sep 17 00:00:00 2001 From: Ahree Hong Date: Tue, 7 Feb 2023 14:26:36 -0800 -Subject: [PATCH 26/40] set hostname for BR nodes +Subject: [PATCH 24/40] set hostname for BR nodes Signed-off-by: Ahree Hong --- @@ -254,5 +254,5 @@ index 83be3a157..4f6bc18af 100644 if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0027-Add-bottlerocket-k8s-settings-support.patch b/projects/kubernetes-sigs/cluster-api/patches/0025-Add-bottlerocket-k8s-settings-support.patch similarity index 55% rename from projects/kubernetes-sigs/cluster-api/patches/0027-Add-bottlerocket-k8s-settings-support.patch rename to projects/kubernetes-sigs/cluster-api/patches/0025-Add-bottlerocket-k8s-settings-support.patch index c7855c2b3a..3e8ff23b9f 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0027-Add-bottlerocket-k8s-settings-support.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0025-Add-bottlerocket-k8s-settings-support.patch @@ -1,27 +1,30 @@ -From 5bd04353b086a1cca114b7bb3ff0f59e0d61a372 Mon Sep 17 00:00:00 2001 +From 7eac371a51ec52e040e809123051e089ffa81568 Mon Sep 17 00:00:00 2001 From: Abhinav Pandey Date: Thu, 2 Mar 2023 10:18:07 -0800 -Subject: [PATCH 27/40] Add bottlerocket k8s settings support +Subject: [PATCH 25/40] Add bottlerocket k8s settings support Signed-off-by: Abhinav Pandey --- api/v1beta1/zz_generated.openapi.go | 22 + - .../api/v1alpha4/zz_generated.conversion.go | 2 + + .../kubeadm/api/v1alpha4/kubeadm_types.go | 30 + + .../api/v1alpha4/zz_generated.conversion.go | 68 +++ + .../api/v1alpha4/zz_generated.deepcopy.go | 55 ++ .../kubeadm/api/v1beta1/kubeadm_types.go | 30 + .../api/v1beta1/zz_generated.deepcopy.go | 55 ++ - ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 52 ++ - ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 54 ++ + ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 156 +++++ + ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 162 ++++++ .../internal/bottlerocket/bootstrap.go | 21 +- .../internal/bottlerocket/bootstrap_test.go | 534 ++++++++++++------ .../internal/bottlerocket/bottlerocket.go | 31 +- .../controllers/kubeadmconfig_controller.go | 4 +- + .../kubeadm/types/upstreamv1beta1/types.go | 30 + + .../upstreamv1beta1/zz_generated.deepcopy.go | 55 ++ .../zz_generated.conversion.go | 2 + .../zz_generated.conversion.go | 2 + - .../api/v1alpha4/zz_generated.deepcopy.go | 2 +- - ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 52 ++ - ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 56 ++ + ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 156 +++++ + ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 112 ++++ .../webhooks/kubeadm_control_plane.go | 2 + - 16 files changed, 736 insertions(+), 185 deletions(-) + 19 files changed, 1343 insertions(+), 184 deletions(-) diff --git a/api/v1beta1/zz_generated.openapi.go b/api/v1beta1/zz_generated.openapi.go index d49f8303a..96fc5fcfb 100644 @@ -63,26 +66,248 @@ index d49f8303a..96fc5fcfb 100644 }, }, }, +diff --git a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +index f1e5eee19..5fe836370 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +@@ -166,6 +166,31 @@ type ClusterConfiguration struct { + // This is only for bottlerocket. + // +optional + BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` ++ ++ // Bottlerocket holds configuration for certain bottlerocket settings. ++ // This is only for bottlerocket. ++ // +optional ++ Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` ++} ++ ++// BottlerocketSettings define bottlerocket settings that can be configured on bottlerocket nodes. ++// This setting is ONLY for bottlerocket nodes. ++type BottlerocketSettings struct { ++ // Kubernetes holds the kubernetes settings for bottlerocket nodes. ++ Kubernetes *BottlerocketKubernetesSettings `json:"kubernetes,omitempty"` ++} ++ ++// BottlerocketKubernetesSettings holds the settings for kubernetes on bottlerocket nodes. ++// This setting is ONLY for bottlerocket nodes. ++type BottlerocketKubernetesSettings struct { ++ // MaxPods defines the maximum number of pods that can run on a node. ++ MaxPods int `json:"maxPods,omitempty"` ++ ++ // AllowedUnsafeSysctls defines the list of unsafe sysctls that can be set on a node. ++ AllowedUnsafeSysctls []string `json:"allowedUnsafeSysctls,omitempty"` ++ ++ // ClusterDNSIPs defines IP addresses of the DNS servers. ++ ClusterDNSIPs []string `json:"clusterDNSIPs,omitempty"` + } + + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. +@@ -486,6 +511,11 @@ type JoinConfiguration struct { + // This is only for bottlerocket. + // +optional + BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` ++ ++ // Bottlerocket holds configuration for certain bottlerocket settings. ++ // This is only for bottlerocket. ++ // +optional ++ Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` + } + + // BottlerocketHostContainer describes a host image for Bottlerocket diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -index 7af108f9e..43971cb70 100644 +index c3bdb3831..bc25ef023 100644 --- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -@@ -730,6 +730,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(i +@@ -140,6 +140,26 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketKubernetesSettings)(nil), (*v1beta1.BottlerocketKubernetesSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings(a.(*BottlerocketKubernetesSettings), b.(*v1beta1.BottlerocketKubernetesSettings), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketKubernetesSettings)(nil), (*BottlerocketKubernetesSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketKubernetesSettings_To_v1alpha4_BottlerocketKubernetesSettings(a.(*v1beta1.BottlerocketKubernetesSettings), b.(*BottlerocketKubernetesSettings), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketSettings)(nil), (*v1beta1.BottlerocketSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_BottlerocketSettings_To_v1beta1_BottlerocketSettings(a.(*BottlerocketSettings), b.(*v1beta1.BottlerocketSettings), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketSettings)(nil), (*BottlerocketSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketSettings_To_v1alpha4_BottlerocketSettings(a.(*v1beta1.BottlerocketSettings), b.(*BottlerocketSettings), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*ClusterConfiguration)(nil), (*v1beta1.ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(a.(*ClusterConfiguration), b.(*v1beta1.ClusterConfiguration), scope) + }); err != nil { +@@ -755,6 +775,50 @@ func Convert_v1beta1_BottlerocketHostContainer_To_v1alpha4_BottlerocketHostConta + return autoConvert_v1beta1_BottlerocketHostContainer_To_v1alpha4_BottlerocketHostContainer(in, out, s) + } + ++func autoConvert_v1alpha4_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings(in *BottlerocketKubernetesSettings, out *v1beta1.BottlerocketKubernetesSettings, s conversion.Scope) error { ++ out.MaxPods = in.MaxPods ++ out.AllowedUnsafeSysctls = *(*[]string)(unsafe.Pointer(&in.AllowedUnsafeSysctls)) ++ out.ClusterDNSIPs = *(*[]string)(unsafe.Pointer(&in.ClusterDNSIPs)) ++ return nil ++} ++ ++// Convert_v1alpha4_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings is an autogenerated conversion function. ++func Convert_v1alpha4_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings(in *BottlerocketKubernetesSettings, out *v1beta1.BottlerocketKubernetesSettings, s conversion.Scope) error { ++ return autoConvert_v1alpha4_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketKubernetesSettings_To_v1alpha4_BottlerocketKubernetesSettings(in *v1beta1.BottlerocketKubernetesSettings, out *BottlerocketKubernetesSettings, s conversion.Scope) error { ++ out.MaxPods = in.MaxPods ++ out.AllowedUnsafeSysctls = *(*[]string)(unsafe.Pointer(&in.AllowedUnsafeSysctls)) ++ out.ClusterDNSIPs = *(*[]string)(unsafe.Pointer(&in.ClusterDNSIPs)) ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketKubernetesSettings_To_v1alpha4_BottlerocketKubernetesSettings is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketKubernetesSettings_To_v1alpha4_BottlerocketKubernetesSettings(in *v1beta1.BottlerocketKubernetesSettings, out *BottlerocketKubernetesSettings, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketKubernetesSettings_To_v1alpha4_BottlerocketKubernetesSettings(in, out, s) ++} ++ ++func autoConvert_v1alpha4_BottlerocketSettings_To_v1beta1_BottlerocketSettings(in *BottlerocketSettings, out *v1beta1.BottlerocketSettings, s conversion.Scope) error { ++ out.Kubernetes = (*v1beta1.BottlerocketKubernetesSettings)(unsafe.Pointer(in.Kubernetes)) ++ return nil ++} ++ ++// Convert_v1alpha4_BottlerocketSettings_To_v1beta1_BottlerocketSettings is an autogenerated conversion function. ++func Convert_v1alpha4_BottlerocketSettings_To_v1beta1_BottlerocketSettings(in *BottlerocketSettings, out *v1beta1.BottlerocketSettings, s conversion.Scope) error { ++ return autoConvert_v1alpha4_BottlerocketSettings_To_v1beta1_BottlerocketSettings(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketSettings_To_v1alpha4_BottlerocketSettings(in *v1beta1.BottlerocketSettings, out *BottlerocketSettings, s conversion.Scope) error { ++ out.Kubernetes = (*BottlerocketKubernetesSettings)(unsafe.Pointer(in.Kubernetes)) ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketSettings_To_v1alpha4_BottlerocketSettings is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketSettings_To_v1alpha4_BottlerocketSettings(in *v1beta1.BottlerocketSettings, out *BottlerocketSettings, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketSettings_To_v1alpha4_BottlerocketSettings(in, out, s) ++} ++ + func autoConvert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *ClusterConfiguration, out *v1beta1.ClusterConfiguration, s conversion.Scope) error { + if err := Convert_v1alpha4_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { + return err +@@ -800,6 +864,7 @@ func autoConvert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(i out.ClusterName = in.ClusterName - // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type - // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type -+ // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type + out.BottlerocketHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]v1beta1.BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) ++ out.Bottlerocket = (*v1beta1.BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) + return nil + } + +@@ -853,6 +918,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(i + out.ClusterName = in.ClusterName + out.BottlerocketHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) ++ out.Bottlerocket = (*BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) return nil } -@@ -1137,6 +1138,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1b +@@ -1228,6 +1294,7 @@ func autoConvert_v1alpha4_JoinConfiguration_To_v1beta1_JoinConfiguration(in *Joi + out.ControlPlane = (*v1beta1.JoinControlPlane)(unsafe.Pointer(in.ControlPlane)) + out.BottlerocketCustomHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]v1beta1.BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) ++ out.Bottlerocket = (*v1beta1.BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) + return nil + } + +@@ -1267,6 +1334,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1b // WARNING: in.Patches requires manual conversion: does not exist in peer-type - // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type - // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type -+ // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type + out.BottlerocketCustomHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) ++ out.Bottlerocket = (*BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) return nil } +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +index 4688180f0..876da90f3 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +@@ -222,6 +222,51 @@ func (in *BottlerocketHostContainer) DeepCopy() *BottlerocketHostContainer { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketKubernetesSettings) DeepCopyInto(out *BottlerocketKubernetesSettings) { ++ *out = *in ++ if in.AllowedUnsafeSysctls != nil { ++ in, out := &in.AllowedUnsafeSysctls, &out.AllowedUnsafeSysctls ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++ if in.ClusterDNSIPs != nil { ++ in, out := &in.ClusterDNSIPs, &out.ClusterDNSIPs ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketKubernetesSettings. ++func (in *BottlerocketKubernetesSettings) DeepCopy() *BottlerocketKubernetesSettings { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketKubernetesSettings) ++ in.DeepCopyInto(out) ++ return out ++} ++ ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketSettings) DeepCopyInto(out *BottlerocketSettings) { ++ *out = *in ++ if in.Kubernetes != nil { ++ in, out := &in.Kubernetes, &out.Kubernetes ++ *out = new(BottlerocketKubernetesSettings) ++ (*in).DeepCopyInto(*out) ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketSettings. ++func (in *BottlerocketSettings) DeepCopy() *BottlerocketSettings { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketSettings) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = *in +@@ -255,6 +300,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = make([]BottlerocketBootstrapContainer, len(*in)) + copy(*out, *in) + } ++ if in.Bottlerocket != nil { ++ in, out := &in.Bottlerocket, &out.Bottlerocket ++ *out = new(BottlerocketSettings) ++ (*in).DeepCopyInto(*out) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. +@@ -629,6 +679,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = make([]BottlerocketBootstrapContainer, len(*in)) + copy(*out, *in) + } ++ if in.Bottlerocket != nil { ++ in, out := &in.Bottlerocket, &out.Bottlerocket ++ *out = new(BottlerocketSettings) ++ (*in).DeepCopyInto(*out) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go index 409d724b3..b3814c089 100644 --- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go @@ -212,10 +437,10 @@ index ca5525885..5e614f3cc 100644 // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -index 78973aca9..6c0a1ff00 100644 +index aad4846c8..811f6c3ee 100644 --- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -@@ -1237,6 +1237,32 @@ spec: +@@ -103,6 +103,32 @@ spec: schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -248,7 +473,7 @@ index 78973aca9..6c0a1ff00 100644 bottlerocketAdmin: description: BottlerocketAdmin holds the image source for admin container This is only for bottlerocket -@@ -2029,6 +2055,32 @@ spec: +@@ -830,6 +856,32 @@ spec: schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -281,112 +506,380 @@ index 78973aca9..6c0a1ff00 100644 bottlerocketAdmin: description: BottlerocketAdmin holds the image source for admin container This is only for bottlerocket -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -index 99af465e7..1bf94de01 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -@@ -1270,6 +1270,33 @@ spec: - convert recognized schemas to the latest internal value, - and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string -+ bottlerocket: -+ description: Bottlerocket holds configuration for certain -+ bottlerocket settings. This is only for bottlerocket. -+ properties: -+ kubernetes: -+ description: Kubernetes holds the kubernetes settings -+ for bottlerocket nodes. -+ properties: -+ allowedUnsafeSysctls: -+ description: AllowedUnsafeSysctls defines the -+ list of unsafe sysctls that can be set on a -+ node. -+ items: -+ type: string -+ type: array -+ clusterDNSIPs: -+ description: ClusterDNSIPs defines IP addresses -+ of the DNS servers. -+ items: -+ type: string -+ type: array -+ maxPods: -+ description: MaxPods defines the maximum number -+ of pods that can run on a node. -+ type: integer -+ type: object -+ type: object - bottlerocketAdmin: - description: BottlerocketAdmin holds the image source - for admin container This is only for bottlerocket -@@ -2118,6 +2145,33 @@ spec: - convert recognized schemas to the latest internal value, - and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string -+ bottlerocket: -+ description: Bottlerocket holds configuration for certain -+ bottlerocket settings. This is only for bottlerocket. -+ properties: -+ kubernetes: -+ description: Kubernetes holds the kubernetes settings -+ for bottlerocket nodes. -+ properties: -+ allowedUnsafeSysctls: -+ description: AllowedUnsafeSysctls defines the -+ list of unsafe sysctls that can be set on a -+ node. -+ items: -+ type: string -+ type: array -+ clusterDNSIPs: -+ description: ClusterDNSIPs defines IP addresses -+ of the DNS servers. -+ items: -+ type: string -+ type: array -+ maxPods: -+ description: MaxPods defines the maximum number -+ of pods that can run on a node. -+ type: integer -+ type: object -+ type: object - bottlerocketAdmin: - description: BottlerocketAdmin holds the image source - for admin container This is only for bottlerocket -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -index 9cf4a909a..e5926de86 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -@@ -10,8 +10,17 @@ standalone-mode = true - authentication-mode = "tls" - server-tls-bootstrap = false - pod-infra-container-image = "{{.PauseContainerSource}}" --{{- if (ne .ProviderId "")}} --provider-id = "{{.ProviderId}}" -+{{- if (ne .ProviderID "")}} -+provider-id = "{{.ProviderID}}" -+{{- end -}} -+{{- if .AllowedUnsafeSysctls }} -+allowed-unsafe-sysctls = [{{stringsJoin .AllowedUnsafeSysctls ", " }}] -+{{- end -}} -+{{- if .ClusterDNSIPs }} -+cluster-dns-ip = [{{stringsJoin .ClusterDNSIPs ", " }}] -+{{- end -}} -+{{- if .MaxPods }} -+max-pods = {{.MaxPods}} - {{- end -}} - {{- end -}} - ` -@@ -20,8 +29,8 @@ provider-id = "{{.ProviderId}}" - [settings.host-containers.{{.Name}}] - enabled = true - superpowered = {{.Superpowered}} --{{- if (ne (imageUrl .ImageMeta) "")}} --source = "{{imageUrl .ImageMeta}}" -+{{- if (ne (imageURL .ImageMeta) "")}} -+source = "{{imageURL .ImageMeta}}" - {{- end -}} - {{- if (ne .UserData "")}} +@@ -1436,6 +1488,32 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain bottlerocket ++ settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings for ++ bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the list of ++ unsafe sysctls that can be set on a node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses of the ++ DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number of pods ++ that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source for admin + container This is only for bottlerocket +@@ -2159,6 +2237,32 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain bottlerocket ++ settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings for ++ bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the list of ++ unsafe sysctls that can be set on a node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses of the ++ DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number of pods ++ that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source for admin + container This is only for bottlerocket +@@ -2763,6 +2867,32 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain bottlerocket ++ settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings for ++ bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the list of ++ unsafe sysctls that can be set on a node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses of the ++ DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number of pods ++ that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source for admin + container This is only for bottlerocket +@@ -3555,6 +3685,32 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain bottlerocket ++ settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings for ++ bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the list of ++ unsafe sysctls that can be set on a node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses of the ++ DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number of pods ++ that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source for admin + container This is only for bottlerocket +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +index 67d0f44e5..18eb3988a 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +@@ -111,6 +111,33 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain ++ bottlerocket settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the ++ list of unsafe sysctls that can be set on a ++ node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses ++ of the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number ++ of pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source + for admin container This is only for bottlerocket +@@ -884,6 +911,33 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain ++ bottlerocket settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the ++ list of unsafe sysctls that can be set on a ++ node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses ++ of the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number ++ of pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source + for admin container This is only for bottlerocket +@@ -1456,6 +1510,33 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain ++ bottlerocket settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the ++ list of unsafe sysctls that can be set on a ++ node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses ++ of the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number ++ of pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source + for admin container This is only for bottlerocket +@@ -2227,6 +2308,33 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain ++ bottlerocket settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the ++ list of unsafe sysctls that can be set on a ++ node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses ++ of the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number ++ of pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source + for admin container This is only for bottlerocket +@@ -2822,6 +2930,33 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain ++ bottlerocket settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the ++ list of unsafe sysctls that can be set on a ++ node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses ++ of the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number ++ of pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source + for admin container This is only for bottlerocket +@@ -3670,6 +3805,33 @@ spec: + convert recognized schemas to the latest internal value, + and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain ++ bottlerocket settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the ++ list of unsafe sysctls that can be set on a ++ node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses ++ of the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number ++ of pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source + for admin container This is only for bottlerocket +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +index 9cf4a909a..e5926de86 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +@@ -10,8 +10,17 @@ standalone-mode = true + authentication-mode = "tls" + server-tls-bootstrap = false + pod-infra-container-image = "{{.PauseContainerSource}}" +-{{- if (ne .ProviderId "")}} +-provider-id = "{{.ProviderId}}" ++{{- if (ne .ProviderID "")}} ++provider-id = "{{.ProviderID}}" ++{{- end -}} ++{{- if .AllowedUnsafeSysctls }} ++allowed-unsafe-sysctls = [{{stringsJoin .AllowedUnsafeSysctls ", " }}] ++{{- end -}} ++{{- if .ClusterDNSIPs }} ++cluster-dns-ip = [{{stringsJoin .ClusterDNSIPs ", " }}] ++{{- end -}} ++{{- if .MaxPods }} ++max-pods = {{.MaxPods}} + {{- end -}} + {{- end -}} + ` +@@ -20,8 +29,8 @@ provider-id = "{{.ProviderId}}" + [settings.host-containers.{{.Name}}] + enabled = true + superpowered = {{.Superpowered}} +-{{- if (ne (imageUrl .ImageMeta) "")}} +-source = "{{imageUrl .ImageMeta}}" ++{{- if (ne (imageURL .ImageMeta) "")}} ++source = "{{imageURL .ImageMeta}}" + {{- end -}} + {{- if (ne .UserData "")}} user-data = "{{.UserData}}" @@ -40,8 +49,8 @@ user-data = "{{.UserData}}" [settings.bootstrap-containers.{{.Name}}] @@ -1139,46 +1632,174 @@ index 658f3a05e..cbab7c7a4 100644 } - return bottlerocketNodeUserData, nil + -+ return generateNodeUserData("InitBottlerocketNode", bottlerocketNodeInitSettingsTemplate, bottlerocketInput) ++ return generateNodeUserData("InitBottlerocketNode", bottlerocketNodeInitSettingsTemplate, bottlerocketInput) + } + + // bottlerocket configuration accepts taints in the format +diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go +index 4f6bc18af..b63a64589 100644 +--- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go ++++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go +@@ -484,6 +484,7 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex + BottlerocketControl: scope.Config.Spec.ClusterConfiguration.BottlerocketControl, + BottlerocketCustomHostContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketHostContainers, + BottlerocketCustomBootstrapContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketCustomBootstrapContainers, ++ BottlerocketSettings: scope.Config.Spec.ClusterConfiguration.Bottlerocket, + Hostname: machine.Name, + } + if scope.Config.Spec.ClusterConfiguration.Proxy.HTTPSProxy != "" { +@@ -508,7 +509,6 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex + if scope.Config.Spec.NTP != nil && scope.Config.Spec.NTP.Enabled != nil && *scope.Config.Spec.NTP.Enabled { + bottlerocketConfig.NTPServers = scope.Config.Spec.NTP.Servers + } +- + } + + clusterdata, err := kubeadmtypes.MarshalClusterConfigurationForVersion(scope.Config.Spec.ClusterConfiguration, parsedVersion) +@@ -709,6 +709,7 @@ func (r *KubeadmConfigReconciler) joinWorker(ctx context.Context, scope *Scope) + BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, + BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, + BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, ++ BottlerocketSettings: scope.Config.Spec.JoinConfiguration.Bottlerocket, + Hostname: machine.Name, + } + if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { +@@ -855,6 +856,7 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S + BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, + BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, + BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, ++ BottlerocketSettings: scope.Config.Spec.JoinConfiguration.Bottlerocket, + Hostname: machine.Name, + } + if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/types.go b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +index 43b0bf856..607810003 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/types.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +@@ -164,6 +164,31 @@ type ClusterConfiguration struct { + // This is only for bottlerocket. + // +optional + BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` ++ ++ // Bottlerocket holds configuration for certain bottlerocket settings. ++ // This is only for bottlerocket. ++ // +optional ++ Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` ++} ++ ++// BottlerocketSettings define bottlerocket settings that can be configured on bottlerocket nodes. ++// This setting is ONLY for bottlerocket nodes. ++type BottlerocketSettings struct { ++ // Kubernetes holds the kubernetes settings for bottlerocket nodes. ++ Kubernetes *BottlerocketKubernetesSettings `json:"kubernetes,omitempty"` ++} ++ ++// BottlerocketKubernetesSettings holds the settings for kubernetes on bottlerocket nodes. ++// This setting is ONLY for bottlerocket nodes. ++type BottlerocketKubernetesSettings struct { ++ // MaxPods defines the maximum number of pods that can run on a node. ++ MaxPods int `json:"maxPods,omitempty"` ++ ++ // AllowedUnsafeSysctls defines the list of unsafe sysctls that can be set on a node. ++ AllowedUnsafeSysctls []string `json:"allowedUnsafeSysctls,omitempty"` ++ ++ // ClusterDNSIPs defines IP addresses of the DNS servers. ++ ClusterDNSIPs []string `json:"clusterDNSIPs,omitempty"` + } + + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. +@@ -475,6 +500,11 @@ type JoinConfiguration struct { + // This is only for bottlerocket. + // +optional + BottlerocketCustomBootstrapContainers []BottlerocketBootstrapContainer `json:"bottlerocketCustomBootstrapContainers,omitempty"` ++ ++ // Bottlerocket holds configuration for certain bottlerocket settings. ++ // This is only for bottlerocket. ++ // +optional ++ Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` + } + + // BottlerocketHostContainer describes a host image for Bottlerocket +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +index ecbb70ea6..c28f28c4c 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +@@ -221,6 +221,51 @@ func (in *BottlerocketHostContainer) DeepCopy() *BottlerocketHostContainer { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketKubernetesSettings) DeepCopyInto(out *BottlerocketKubernetesSettings) { ++ *out = *in ++ if in.AllowedUnsafeSysctls != nil { ++ in, out := &in.AllowedUnsafeSysctls, &out.AllowedUnsafeSysctls ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++ if in.ClusterDNSIPs != nil { ++ in, out := &in.ClusterDNSIPs, &out.ClusterDNSIPs ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketKubernetesSettings. ++func (in *BottlerocketKubernetesSettings) DeepCopy() *BottlerocketKubernetesSettings { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketKubernetesSettings) ++ in.DeepCopyInto(out) ++ return out ++} ++ ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketSettings) DeepCopyInto(out *BottlerocketSettings) { ++ *out = *in ++ if in.Kubernetes != nil { ++ in, out := &in.Kubernetes, &out.Kubernetes ++ *out = new(BottlerocketKubernetesSettings) ++ (*in).DeepCopyInto(*out) ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketSettings. ++func (in *BottlerocketSettings) DeepCopy() *BottlerocketSettings { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketSettings) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = *in +@@ -254,6 +299,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = make([]BottlerocketBootstrapContainer, len(*in)) + copy(*out, *in) + } ++ if in.Bottlerocket != nil { ++ in, out := &in.Bottlerocket, &out.Bottlerocket ++ *out = new(BottlerocketSettings) ++ (*in).DeepCopyInto(*out) ++ } } - // bottlerocket configuration accepts taints in the format -diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -index 4f6bc18af..b63a64589 100644 ---- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -+++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -@@ -484,6 +484,7 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex - BottlerocketControl: scope.Config.Spec.ClusterConfiguration.BottlerocketControl, - BottlerocketCustomHostContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketHostContainers, - BottlerocketCustomBootstrapContainers: scope.Config.Spec.ClusterConfiguration.BottlerocketCustomBootstrapContainers, -+ BottlerocketSettings: scope.Config.Spec.ClusterConfiguration.Bottlerocket, - Hostname: machine.Name, - } - if scope.Config.Spec.ClusterConfiguration.Proxy.HTTPSProxy != "" { -@@ -508,7 +509,6 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex - if scope.Config.Spec.NTP != nil && scope.Config.Spec.NTP.Enabled != nil && *scope.Config.Spec.NTP.Enabled { - bottlerocketConfig.NTPServers = scope.Config.Spec.NTP.Servers - } -- + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. +@@ -528,6 +578,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = make([]BottlerocketBootstrapContainer, len(*in)) + copy(*out, *in) } ++ if in.Bottlerocket != nil { ++ in, out := &in.Bottlerocket, &out.Bottlerocket ++ *out = new(BottlerocketSettings) ++ (*in).DeepCopyInto(*out) ++ } + } - clusterdata, err := kubeadmtypes.MarshalClusterConfigurationForVersion(scope.Config.Spec.ClusterConfiguration, parsedVersion) -@@ -709,6 +709,7 @@ func (r *KubeadmConfigReconciler) joinWorker(ctx context.Context, scope *Scope) - BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, - BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, - BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, -+ BottlerocketSettings: scope.Config.Spec.JoinConfiguration.Bottlerocket, - Hostname: machine.Name, - } - if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { -@@ -855,6 +856,7 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S - BottlerocketControl: scope.Config.Spec.JoinConfiguration.BottlerocketControl, - BottlerocketCustomHostContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomHostContainers, - BottlerocketCustomBootstrapContainers: scope.Config.Spec.JoinConfiguration.BottlerocketCustomBootstrapContainers, -+ BottlerocketSettings: scope.Config.Spec.JoinConfiguration.Bottlerocket, - Hostname: machine.Name, - } - if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go index 8b6475592..8b1acbb57 100644 --- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go @@ -1219,24 +1840,143 @@ index 4584e6266..c613bdd12 100644 return nil } -diff --git a/controlplane/kubeadm/api/v1alpha4/zz_generated.deepcopy.go b/controlplane/kubeadm/api/v1alpha4/zz_generated.deepcopy.go -index 4ad231410..df2807f5d 100644 ---- a/controlplane/kubeadm/api/v1alpha4/zz_generated.deepcopy.go -+++ b/controlplane/kubeadm/api/v1alpha4/zz_generated.deepcopy.go -@@ -22,7 +22,7 @@ package v1alpha4 - - import ( - "k8s.io/apimachinery/pkg/apis/meta/v1" -- "k8s.io/apimachinery/pkg/runtime" -+ runtime "k8s.io/apimachinery/pkg/runtime" - "k8s.io/apimachinery/pkg/util/intstr" - apiv1alpha4 "sigs.k8s.io/cluster-api/api/v1alpha4" - ) diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -index e0aaa6532..5ed727e20 100644 +index 119558689..cda7db3f5 100644 --- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -@@ -1515,6 +1515,32 @@ spec: +@@ -178,6 +178,32 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain ++ bottlerocket settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the list ++ of unsafe sysctls that can be set on a node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses of ++ the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number of ++ pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source for + admin container This is only for bottlerocket +@@ -935,6 +961,32 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain ++ bottlerocket settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the list ++ of unsafe sysctls that can be set on a node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses of ++ the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number of ++ pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source for + admin container This is only for bottlerocket +@@ -1678,6 +1730,32 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain ++ bottlerocket settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the list ++ of unsafe sysctls that can be set on a node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses of ++ the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number of ++ pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source for + admin container This is only for bottlerocket +@@ -2432,6 +2510,32 @@ spec: + schemas to the latest internal value, and may reject unrecognized + values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for certain ++ bottlerocket settings. This is only for bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines the list ++ of unsafe sysctls that can be set on a node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses of ++ the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number of ++ pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source for + admin container This is only for bottlerocket +@@ -3259,6 +3363,32 @@ spec: schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -1269,7 +2009,7 @@ index e0aaa6532..5ed727e20 100644 bottlerocketAdmin: description: BottlerocketAdmin holds the image source for admin container This is only for bottlerocket -@@ -2342,6 +2368,32 @@ spec: +@@ -4086,6 +4216,32 @@ spec: schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -1303,10 +2043,80 @@ index e0aaa6532..5ed727e20 100644 description: BottlerocketAdmin holds the image source for admin container This is only for bottlerocket diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -index e7647e47a..90ddceaaf 100644 +index 66e39e74a..055b51899 100644 --- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -@@ -1468,6 +1468,34 @@ spec: +@@ -125,6 +125,34 @@ spec: + value, and may reject unrecognized values. More + info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for ++ certain bottlerocket settings. This is only for ++ bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines ++ the list of unsafe sysctls that can be set ++ on a node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses ++ of the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number ++ of pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source + for admin container This is only for bottlerocket +@@ -930,6 +958,34 @@ spec: + value, and may reject unrecognized values. More + info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string ++ bottlerocket: ++ description: Bottlerocket holds configuration for ++ certain bottlerocket settings. This is only for ++ bottlerocket. ++ properties: ++ kubernetes: ++ description: Kubernetes holds the kubernetes settings ++ for bottlerocket nodes. ++ properties: ++ allowedUnsafeSysctls: ++ description: AllowedUnsafeSysctls defines ++ the list of unsafe sysctls that can be set ++ on a node. ++ items: ++ type: string ++ type: array ++ clusterDNSIPs: ++ description: ClusterDNSIPs defines IP addresses ++ of the DNS servers. ++ items: ++ type: string ++ type: array ++ maxPods: ++ description: MaxPods defines the maximum number ++ of pods that can run on a node. ++ type: integer ++ type: object ++ type: object + bottlerocketAdmin: + description: BottlerocketAdmin holds the image source + for admin container This is only for bottlerocket +@@ -1692,6 +1748,34 @@ spec: value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -1341,7 +2151,7 @@ index e7647e47a..90ddceaaf 100644 bottlerocketAdmin: description: BottlerocketAdmin holds the image source for admin container This is only for bottlerocket -@@ -2352,6 +2380,34 @@ spec: +@@ -2576,6 +2660,34 @@ spec: value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' type: string @@ -1397,5 +2207,5 @@ index 553220d8a..0aaf0c3a5 100644 // spec.kubeadmConfigSpec {spec, kubeadmConfigSpec, preKubeadmCommands}, -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0026-add-br-kernel.sysctl-settings.patch b/projects/kubernetes-sigs/cluster-api/patches/0026-add-br-kernel.sysctl-settings.patch new file mode 100644 index 0000000000..170849b2a8 --- /dev/null +++ b/projects/kubernetes-sigs/cluster-api/patches/0026-add-br-kernel.sysctl-settings.patch @@ -0,0 +1,1426 @@ +From 5fb56abd889b2307a62426b2e910232aa4600a0b Mon Sep 17 00:00:00 2001 +From: Ahree Hong +Date: Tue, 7 Mar 2023 14:01:39 -0800 +Subject: [PATCH 26/40] add br kernel.sysctl settings + +Signed-off-by: Ahree Hong +--- + .../kubeadm/api/v1alpha4/kubeadm_types.go | 10 + + .../api/v1alpha4/zz_generated.conversion.go | 32 ++ + .../api/v1alpha4/zz_generated.deepcopy.go | 27 + + .../kubeadm/api/v1beta1/kubeadm_types.go | 10 + + .../api/v1beta1/zz_generated.deepcopy.go | 27 + + ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 66 +++ + ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 66 +++ + .../internal/bottlerocket/bootstrap.go | 10 + + .../internal/bottlerocket/bootstrap_test.go | 48 ++ + .../internal/bottlerocket/bottlerocket.go | 32 +- + .../kubeadm/types/upstreamv1beta1/types.go | 10 + + .../zz_generated.conversion.go | 462 ++++++++++++++++++ + .../upstreamv1beta1/zz_generated.deepcopy.go | 27 + + ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 66 +++ + ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 48 ++ + 15 files changed, 934 insertions(+), 7 deletions(-) + +diff --git a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +index 5fe836370..c00ea0a53 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +@@ -178,6 +178,10 @@ type ClusterConfiguration struct { + type BottlerocketSettings struct { + // Kubernetes holds the kubernetes settings for bottlerocket nodes. + Kubernetes *BottlerocketKubernetesSettings `json:"kubernetes,omitempty"` ++ ++ // KernelSettings contains additional kernel settings for Bottlerocket. ++ // +optional ++ Kernel *BottlerocketKernelSettings `json:"kernel,omitempty"` + } + + // BottlerocketKubernetesSettings holds the settings for kubernetes on bottlerocket nodes. +@@ -193,6 +197,12 @@ type BottlerocketKubernetesSettings struct { + ClusterDNSIPs []string `json:"clusterDNSIPs,omitempty"` + } + ++// BottlerocketKernelSettings holds the kernel settings for bottlerocket nodes ++type BottlerocketKernelSettings struct { ++ // SysctlSettings defines the kernel sysctl settings to set for bottlerocket nodes. ++ SysctlSettings map[string]string `json:"sysctlSettings,omitempty"` ++} ++ + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. + // This setting is ONLY for bottlerocket nodes, as this needs to be set pre-boot time along with user-data + type Pause struct { +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +index bc25ef023..70c06fcf3 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +@@ -140,6 +140,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketKernelSettings)(nil), (*v1beta1.BottlerocketKernelSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_BottlerocketKernelSettings_To_v1beta1_BottlerocketKernelSettings(a.(*BottlerocketKernelSettings), b.(*v1beta1.BottlerocketKernelSettings), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketKernelSettings)(nil), (*BottlerocketKernelSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketKernelSettings_To_v1alpha4_BottlerocketKernelSettings(a.(*v1beta1.BottlerocketKernelSettings), b.(*BottlerocketKernelSettings), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*BottlerocketKubernetesSettings)(nil), (*v1beta1.BottlerocketKubernetesSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1alpha4_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings(a.(*BottlerocketKubernetesSettings), b.(*v1beta1.BottlerocketKubernetesSettings), scope) + }); err != nil { +@@ -775,6 +785,26 @@ func Convert_v1beta1_BottlerocketHostContainer_To_v1alpha4_BottlerocketHostConta + return autoConvert_v1beta1_BottlerocketHostContainer_To_v1alpha4_BottlerocketHostContainer(in, out, s) + } + ++func autoConvert_v1alpha4_BottlerocketKernelSettings_To_v1beta1_BottlerocketKernelSettings(in *BottlerocketKernelSettings, out *v1beta1.BottlerocketKernelSettings, s conversion.Scope) error { ++ out.SysctlSettings = *(*map[string]string)(unsafe.Pointer(&in.SysctlSettings)) ++ return nil ++} ++ ++// Convert_v1alpha4_BottlerocketKernelSettings_To_v1beta1_BottlerocketKernelSettings is an autogenerated conversion function. ++func Convert_v1alpha4_BottlerocketKernelSettings_To_v1beta1_BottlerocketKernelSettings(in *BottlerocketKernelSettings, out *v1beta1.BottlerocketKernelSettings, s conversion.Scope) error { ++ return autoConvert_v1alpha4_BottlerocketKernelSettings_To_v1beta1_BottlerocketKernelSettings(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketKernelSettings_To_v1alpha4_BottlerocketKernelSettings(in *v1beta1.BottlerocketKernelSettings, out *BottlerocketKernelSettings, s conversion.Scope) error { ++ out.SysctlSettings = *(*map[string]string)(unsafe.Pointer(&in.SysctlSettings)) ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketKernelSettings_To_v1alpha4_BottlerocketKernelSettings is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketKernelSettings_To_v1alpha4_BottlerocketKernelSettings(in *v1beta1.BottlerocketKernelSettings, out *BottlerocketKernelSettings, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketKernelSettings_To_v1alpha4_BottlerocketKernelSettings(in, out, s) ++} ++ + func autoConvert_v1alpha4_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings(in *BottlerocketKubernetesSettings, out *v1beta1.BottlerocketKubernetesSettings, s conversion.Scope) error { + out.MaxPods = in.MaxPods + out.AllowedUnsafeSysctls = *(*[]string)(unsafe.Pointer(&in.AllowedUnsafeSysctls)) +@@ -801,6 +831,7 @@ func Convert_v1beta1_BottlerocketKubernetesSettings_To_v1alpha4_BottlerocketKube + + func autoConvert_v1alpha4_BottlerocketSettings_To_v1beta1_BottlerocketSettings(in *BottlerocketSettings, out *v1beta1.BottlerocketSettings, s conversion.Scope) error { + out.Kubernetes = (*v1beta1.BottlerocketKubernetesSettings)(unsafe.Pointer(in.Kubernetes)) ++ out.Kernel = (*v1beta1.BottlerocketKernelSettings)(unsafe.Pointer(in.Kernel)) + return nil + } + +@@ -811,6 +842,7 @@ func Convert_v1alpha4_BottlerocketSettings_To_v1beta1_BottlerocketSettings(in *B + + func autoConvert_v1beta1_BottlerocketSettings_To_v1alpha4_BottlerocketSettings(in *v1beta1.BottlerocketSettings, out *BottlerocketSettings, s conversion.Scope) error { + out.Kubernetes = (*BottlerocketKubernetesSettings)(unsafe.Pointer(in.Kubernetes)) ++ out.Kernel = (*BottlerocketKernelSettings)(unsafe.Pointer(in.Kernel)) + return nil + } + +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +index 876da90f3..44bbe16ce 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +@@ -222,6 +222,28 @@ func (in *BottlerocketHostContainer) DeepCopy() *BottlerocketHostContainer { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketKernelSettings) DeepCopyInto(out *BottlerocketKernelSettings) { ++ *out = *in ++ if in.SysctlSettings != nil { ++ in, out := &in.SysctlSettings, &out.SysctlSettings ++ *out = make(map[string]string, len(*in)) ++ for key, val := range *in { ++ (*out)[key] = val ++ } ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketKernelSettings. ++func (in *BottlerocketKernelSettings) DeepCopy() *BottlerocketKernelSettings { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketKernelSettings) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketKubernetesSettings) DeepCopyInto(out *BottlerocketKubernetesSettings) { + *out = *in +@@ -255,6 +277,11 @@ func (in *BottlerocketSettings) DeepCopyInto(out *BottlerocketSettings) { + *out = new(BottlerocketKubernetesSettings) + (*in).DeepCopyInto(*out) + } ++ if in.Kernel != nil { ++ in, out := &in.Kernel, &out.Kernel ++ *out = new(BottlerocketKernelSettings) ++ (*in).DeepCopyInto(*out) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketSettings. +diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +index b3814c089..c97ef8604 100644 +--- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +@@ -197,6 +197,10 @@ type ClusterConfiguration struct { + type BottlerocketSettings struct { + // Kubernetes holds the kubernetes settings for bottlerocket nodes. + Kubernetes *BottlerocketKubernetesSettings `json:"kubernetes,omitempty"` ++ ++ // KernelSettings contains additional kernel settings for Bottlerocket. ++ // +optional ++ Kernel *BottlerocketKernelSettings `json:"kernel,omitempty"` + } + + // BottlerocketKubernetesSettings holds the settings for kubernetes on bottlerocket nodes. +@@ -212,6 +216,12 @@ type BottlerocketKubernetesSettings struct { + ClusterDNSIPs []string `json:"clusterDNSIPs,omitempty"` + } + ++// BottlerocketKernelSettings holds the kernel settings for bottlerocket nodes ++type BottlerocketKernelSettings struct { ++ // SysctlSettings defines the kernel sysctl settings to set for bottlerocket nodes. ++ SysctlSettings map[string]string `json:"sysctlSettings,omitempty"` ++} ++ + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. + // This setting is ONLY for bottlerocket nodes, as this needs to be set pre-boot time along with user-data + type Pause struct { +diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +index 5e614f3cc..d335a35b1 100644 +--- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +@@ -222,6 +222,28 @@ func (in *BottlerocketHostContainer) DeepCopy() *BottlerocketHostContainer { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketKernelSettings) DeepCopyInto(out *BottlerocketKernelSettings) { ++ *out = *in ++ if in.SysctlSettings != nil { ++ in, out := &in.SysctlSettings, &out.SysctlSettings ++ *out = make(map[string]string, len(*in)) ++ for key, val := range *in { ++ (*out)[key] = val ++ } ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketKernelSettings. ++func (in *BottlerocketKernelSettings) DeepCopy() *BottlerocketKernelSettings { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketKernelSettings) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketKubernetesSettings) DeepCopyInto(out *BottlerocketKubernetesSettings) { + *out = *in +@@ -255,6 +277,11 @@ func (in *BottlerocketSettings) DeepCopyInto(out *BottlerocketSettings) { + *out = new(BottlerocketKubernetesSettings) + (*in).DeepCopyInto(*out) + } ++ if in.Kernel != nil { ++ in, out := &in.Kernel, &out.Kernel ++ *out = new(BottlerocketKernelSettings) ++ (*in).DeepCopyInto(*out) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketSettings. +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +index 811f6c3ee..13eab82cd 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +@@ -107,6 +107,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel settings ++ for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings for + bottlerocket nodes. +@@ -860,6 +871,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel settings ++ for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings for + bottlerocket nodes. +@@ -1492,6 +1514,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel settings ++ for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings for + bottlerocket nodes. +@@ -2241,6 +2274,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel settings ++ for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings for + bottlerocket nodes. +@@ -2871,6 +2915,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel settings ++ for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings for + bottlerocket nodes. +@@ -3689,6 +3744,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel settings ++ for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings for + bottlerocket nodes. +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +index 18eb3988a..02cc4c0ed 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +@@ -115,6 +115,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel ++ sysctl settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -915,6 +926,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel ++ sysctl settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -1514,6 +1536,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel ++ sysctl settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -2312,6 +2345,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel ++ sysctl settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -2934,6 +2978,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel ++ sysctl settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -3809,6 +3864,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel ++ sysctl settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +index e5926de86..a23a43668 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +@@ -113,6 +113,12 @@ password = "{{.RegistryMirrorPassword}}" + [settings.ntp] + time-servers = [{{stringsJoin .NTPServers ", " }}] + {{- end -}} ++` ++ ++ sysctlSettingsTemplate = `{{ define "sysctlSettingsTemplate" -}} ++[settings.kernel.sysctl] ++{{.SysctlSettings}} ++{{- end -}} + ` + + bottlerocketNodeInitSettingsTemplate = `{{template "hostContainerSlice" .}} +@@ -149,5 +155,9 @@ time-servers = [{{stringsJoin .NTPServers ", " }}] + {{- if .NTPServers}} + {{template "ntpSettings" .}} + {{- end -}} ++ ++{{- if (ne .SysctlSettings "")}} ++{{template "sysctlSettingsTemplate" .}} ++{{- end -}} + ` + ) +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +index 3463a2769..fdc60204d 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +@@ -253,6 +253,33 @@ essential = false + mode = "MODE" + source = "BOOTSTRAP_REPO:BOOTSTRAP_TAG" + user-data = "BOOTSTRAP_B6_4USERDATA"` ++ ++ kernelSettingsUserData = ` ++[settings.host-containers.admin] ++enabled = true ++superpowered = true ++source = "ADMIN_REPO:ADMIN_TAG" ++user-data = "CnsKCSJzc2giOiB7CgkJImF1dGhvcml6ZWQta2V5cyI6IFsic3NoLXJzYSBBQUEuLi4iXQoJfQp9" ++[settings.host-containers.kubeadm-bootstrap] ++enabled = true ++superpowered = true ++source = "BOOTSTRAP_REPO:BOOTSTRAP_TAG" ++user-data = "Qk9UVExFUk9DS0VUX0JPT1RTVFJBUF9VU0VSREFUQQ==" ++ ++[settings.kubernetes] ++cluster-domain = "cluster.local" ++standalone-mode = true ++authentication-mode = "tls" ++server-tls-bootstrap = false ++pod-infra-container-image = "PAUSE_REPO:PAUSE_TAG" ++provider-id = "PROVIDERID" ++ ++[settings.network] ++hostname = "hostname" ++[settings.kernel.sysctl] ++"foo" = "bar" ++"abc" = "def" ++` + ) + + var ( +@@ -465,6 +492,27 @@ func TestGetBottlerocketNodeUserData(t *testing.T) { + }, + output: customBootstrapUserData, + }, ++ { ++ name: "with kernel settings", ++ config: &BottlerocketConfig{ ++ BottlerocketAdmin: brAdmin, ++ BottlerocketBootstrap: brBootstrap, ++ Hostname: hostname, ++ Pause: pause, ++ KubeletExtraArgs: map[string]string{ ++ "provider-id": "PROVIDERID", ++ }, ++ BottlerocketSettings: &bootstrapv1.BottlerocketSettings{ ++ Kernel: &bootstrapv1.BottlerocketKernelSettings{ ++ SysctlSettings: map[string]string{ ++ "foo": "bar", ++ "abc": "def", ++ }, ++ }, ++ }, ++ }, ++ output: kernelSettingsUserData, ++ }, + } + for _, testcase := range testcases { + t.Run(testcase.name, func(t *testing.T) { +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +index cbab7c7a4..afd854f1c 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +@@ -55,10 +55,11 @@ type BottlerocketSettingsInput struct { + ProviderID string + Hostname string + AllowedUnsafeSysctls []string +- ClusterDNSIPs []string ++ ClusterDNSIPs []string + MaxPods int + HostContainers []bootstrapv1.BottlerocketHostContainer + BootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer ++ SysctlSettings string + } + + // HostPath holds the path and type of a host path volume. +@@ -156,6 +157,9 @@ func generateNodeUserData(kind string, tpl string, data interface{}) ([]byte, er + if _, err := tm.Parse(ntpTemplate); err != nil { + return nil, errors.Wrapf(err, "failed to parse NTP %s template", kind) + } ++ if _, err := tm.Parse(sysctlSettingsTemplate); err != nil { ++ return nil, errors.Wrapf(err, "failed to parse sysctl settings %s template", kind) ++ } + t, err := tm.Parse(tpl) + if err != nil { + return nil, errors.Wrapf(err, "failed to parse %s template", kind) +@@ -239,14 +243,20 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot + bottlerocketInput.NTPServers = append(bottlerocketInput.NTPServers, strconv.Quote(ntp)) + } + } +- if config.BottlerocketSettings != nil && config.BottlerocketSettings.Kubernetes != nil { +- bottlerocketInput.MaxPods = config.BottlerocketSettings.Kubernetes.MaxPods +- for _, sysctl := range config.BottlerocketSettings.Kubernetes.AllowedUnsafeSysctls { +- bottlerocketInput.AllowedUnsafeSysctls = append(bottlerocketInput.AllowedUnsafeSysctls, strconv.Quote(sysctl)) ++ if config.BottlerocketSettings != nil { ++ if config.BottlerocketSettings.Kubernetes != nil { ++ bottlerocketInput.MaxPods = config.BottlerocketSettings.Kubernetes.MaxPods ++ for _, sysctl := range config.BottlerocketSettings.Kubernetes.AllowedUnsafeSysctls { ++ bottlerocketInput.AllowedUnsafeSysctls = append(bottlerocketInput.AllowedUnsafeSysctls, strconv.Quote(sysctl)) ++ } ++ for _, ip := range config.BottlerocketSettings.Kubernetes.ClusterDNSIPs { ++ bottlerocketInput.ClusterDNSIPs = append(bottlerocketInput.ClusterDNSIPs, strconv.Quote(ip)) ++ } + } +- for _, ip := range config.BottlerocketSettings.Kubernetes.ClusterDNSIPs { +- bottlerocketInput.ClusterDNSIPs = append(bottlerocketInput.ClusterDNSIPs, strconv.Quote(ip)) ++ if config.BottlerocketSettings.Kernel != nil { ++ bottlerocketInput.SysctlSettings = parseSysctlSettings(config.BottlerocketSettings.Kernel.SysctlSettings) + } ++ + } + + return generateNodeUserData("InitBottlerocketNode", bottlerocketNodeInitSettingsTemplate, bottlerocketInput) +@@ -297,6 +307,14 @@ func parseNodeLabels(nodeLabels string) string { + return nodeLabelsToml + } + ++func parseSysctlSettings(sysctlSettings map[string]string) string { ++ sysctlSettingsToml := "" ++ for key, value := range sysctlSettings { ++ sysctlSettingsToml += fmt.Sprintf("\"%v\" = \"%v\"\n", key, value) ++ } ++ return sysctlSettingsToml ++} ++ + // Parses through all the users and return list of all user's authorized ssh keys + func getAllAuthorizedKeys(users []bootstrapv1.User) string { + var sshAuthorizedKeys []string +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/types.go b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +index 607810003..4563d15de 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/types.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +@@ -176,6 +176,10 @@ type ClusterConfiguration struct { + type BottlerocketSettings struct { + // Kubernetes holds the kubernetes settings for bottlerocket nodes. + Kubernetes *BottlerocketKubernetesSettings `json:"kubernetes,omitempty"` ++ ++ // KernelSettings contains additional kernel settings for Bottlerocket. ++ // +optional ++ Kernel *BottlerocketKernelSettings `json:"kernel,omitempty"` + } + + // BottlerocketKubernetesSettings holds the settings for kubernetes on bottlerocket nodes. +@@ -191,6 +195,12 @@ type BottlerocketKubernetesSettings struct { + ClusterDNSIPs []string `json:"clusterDNSIPs,omitempty"` + } + ++// BottlerocketKernelSettings holds the kernel settings for bottlerocket nodes ++type BottlerocketKernelSettings struct { ++ // SysctlSettings defines the kernel sysctl settings to set for bottlerocket nodes. ++ SysctlSettings map[string]string `json:"sysctlSettings,omitempty"` ++} ++ + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. + // This setting is ONLY for bottlerocket nodes, as this needs to be set pre-boot time along with user-data + type Pause struct { +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go +index 0497d927b..905b58372 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go +@@ -88,6 +88,86 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketAdmin)(nil), (*v1beta1.BottlerocketAdmin)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(a.(*BottlerocketAdmin), b.(*v1beta1.BottlerocketAdmin), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketAdmin)(nil), (*BottlerocketAdmin)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketAdmin_To_upstreamv1beta1_BottlerocketAdmin(a.(*v1beta1.BottlerocketAdmin), b.(*BottlerocketAdmin), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrap)(nil), (*v1beta1.BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(a.(*BottlerocketBootstrap), b.(*v1beta1.BottlerocketBootstrap), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketBootstrap)(nil), (*BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta1_BottlerocketBootstrap(a.(*v1beta1.BottlerocketBootstrap), b.(*BottlerocketBootstrap), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrapContainer)(nil), (*v1beta1.BottlerocketBootstrapContainer)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_BottlerocketBootstrapContainer_To_v1beta1_BottlerocketBootstrapContainer(a.(*BottlerocketBootstrapContainer), b.(*v1beta1.BottlerocketBootstrapContainer), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketBootstrapContainer)(nil), (*BottlerocketBootstrapContainer)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketBootstrapContainer_To_upstreamv1beta1_BottlerocketBootstrapContainer(a.(*v1beta1.BottlerocketBootstrapContainer), b.(*BottlerocketBootstrapContainer), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketControl)(nil), (*v1beta1.BottlerocketControl)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_BottlerocketControl_To_v1beta1_BottlerocketControl(a.(*BottlerocketControl), b.(*v1beta1.BottlerocketControl), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketControl)(nil), (*BottlerocketControl)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketControl_To_upstreamv1beta1_BottlerocketControl(a.(*v1beta1.BottlerocketControl), b.(*BottlerocketControl), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketHostContainer)(nil), (*v1beta1.BottlerocketHostContainer)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_BottlerocketHostContainer_To_v1beta1_BottlerocketHostContainer(a.(*BottlerocketHostContainer), b.(*v1beta1.BottlerocketHostContainer), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketHostContainer)(nil), (*BottlerocketHostContainer)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketHostContainer_To_upstreamv1beta1_BottlerocketHostContainer(a.(*v1beta1.BottlerocketHostContainer), b.(*BottlerocketHostContainer), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketKernelSettings)(nil), (*v1beta1.BottlerocketKernelSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_BottlerocketKernelSettings_To_v1beta1_BottlerocketKernelSettings(a.(*BottlerocketKernelSettings), b.(*v1beta1.BottlerocketKernelSettings), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketKernelSettings)(nil), (*BottlerocketKernelSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketKernelSettings_To_upstreamv1beta1_BottlerocketKernelSettings(a.(*v1beta1.BottlerocketKernelSettings), b.(*BottlerocketKernelSettings), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketKubernetesSettings)(nil), (*v1beta1.BottlerocketKubernetesSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings(a.(*BottlerocketKubernetesSettings), b.(*v1beta1.BottlerocketKubernetesSettings), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketKubernetesSettings)(nil), (*BottlerocketKubernetesSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketKubernetesSettings_To_upstreamv1beta1_BottlerocketKubernetesSettings(a.(*v1beta1.BottlerocketKubernetesSettings), b.(*BottlerocketKubernetesSettings), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketSettings)(nil), (*v1beta1.BottlerocketSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_BottlerocketSettings_To_v1beta1_BottlerocketSettings(a.(*BottlerocketSettings), b.(*v1beta1.BottlerocketSettings), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketSettings)(nil), (*BottlerocketSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketSettings_To_upstreamv1beta1_BottlerocketSettings(a.(*v1beta1.BottlerocketSettings), b.(*BottlerocketSettings), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*v1beta1.ClusterConfiguration)(nil), (*ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_ClusterConfiguration_To_upstreamv1beta1_ClusterConfiguration(a.(*v1beta1.ClusterConfiguration), b.(*ClusterConfiguration), scope) + }); err != nil { +@@ -223,6 +303,36 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*Pause)(nil), (*v1beta1.Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_Pause_To_v1beta1_Pause(a.(*Pause), b.(*v1beta1.Pause), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.Pause)(nil), (*Pause)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_Pause_To_upstreamv1beta1_Pause(a.(*v1beta1.Pause), b.(*Pause), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*ProxyConfiguration)(nil), (*v1beta1.ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_ProxyConfiguration_To_v1beta1_ProxyConfiguration(a.(*ProxyConfiguration), b.(*v1beta1.ProxyConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.ProxyConfiguration)(nil), (*ProxyConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta1_ProxyConfiguration(a.(*v1beta1.ProxyConfiguration), b.(*ProxyConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*RegistryMirrorConfiguration)(nil), (*v1beta1.RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(a.(*RegistryMirrorConfiguration), b.(*v1beta1.RegistryMirrorConfiguration), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.RegistryMirrorConfiguration)(nil), (*RegistryMirrorConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta1_RegistryMirrorConfiguration(a.(*v1beta1.RegistryMirrorConfiguration), b.(*RegistryMirrorConfiguration), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddConversionFunc((*ClusterConfiguration)(nil), (*v1beta1.ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_upstreamv1beta1_ClusterConfiguration_To_v1beta1_ClusterConfiguration(a.(*ClusterConfiguration), b.(*v1beta1.ClusterConfiguration), scope) + }); err != nil { +@@ -379,7 +489,225 @@ func Convert_v1beta1_BootstrapTokenString_To_upstreamv1beta1_BootstrapTokenStrin + return autoConvert_v1beta1_BootstrapTokenString_To_upstreamv1beta1_BootstrapTokenString(in, out, s) + } + ++func autoConvert_upstreamv1beta1_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(in *BottlerocketAdmin, out *v1beta1.BottlerocketAdmin, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta1_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_upstreamv1beta1_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin is an autogenerated conversion function. ++func Convert_upstreamv1beta1_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(in *BottlerocketAdmin, out *v1beta1.BottlerocketAdmin, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketAdmin_To_upstreamv1beta1_BottlerocketAdmin(in *v1beta1.BottlerocketAdmin, out *BottlerocketAdmin, s conversion.Scope) error { ++ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketAdmin_To_upstreamv1beta1_BottlerocketAdmin is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketAdmin_To_upstreamv1beta1_BottlerocketAdmin(in *v1beta1.BottlerocketAdmin, out *BottlerocketAdmin, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketAdmin_To_upstreamv1beta1_BottlerocketAdmin(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta1_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta1_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_upstreamv1beta1_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap is an autogenerated conversion function. ++func Convert_upstreamv1beta1_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta1_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { ++ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta1_BottlerocketBootstrap is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta1_BottlerocketBootstrap(in *v1beta1.BottlerocketBootstrap, out *BottlerocketBootstrap, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta1_BottlerocketBootstrap(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta1_BottlerocketBootstrapContainer_To_v1beta1_BottlerocketBootstrapContainer(in *BottlerocketBootstrapContainer, out *v1beta1.BottlerocketBootstrapContainer, s conversion.Scope) error { ++ out.Name = in.Name ++ if err := Convert_upstreamv1beta1_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ out.Essential = in.Essential ++ out.Mode = in.Mode ++ out.UserData = in.UserData ++ return nil ++} ++ ++// Convert_upstreamv1beta1_BottlerocketBootstrapContainer_To_v1beta1_BottlerocketBootstrapContainer is an autogenerated conversion function. ++func Convert_upstreamv1beta1_BottlerocketBootstrapContainer_To_v1beta1_BottlerocketBootstrapContainer(in *BottlerocketBootstrapContainer, out *v1beta1.BottlerocketBootstrapContainer, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_BottlerocketBootstrapContainer_To_v1beta1_BottlerocketBootstrapContainer(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketBootstrapContainer_To_upstreamv1beta1_BottlerocketBootstrapContainer(in *v1beta1.BottlerocketBootstrapContainer, out *BottlerocketBootstrapContainer, s conversion.Scope) error { ++ out.Name = in.Name ++ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ out.Essential = in.Essential ++ out.Mode = in.Mode ++ out.UserData = in.UserData ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketBootstrapContainer_To_upstreamv1beta1_BottlerocketBootstrapContainer is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketBootstrapContainer_To_upstreamv1beta1_BottlerocketBootstrapContainer(in *v1beta1.BottlerocketBootstrapContainer, out *BottlerocketBootstrapContainer, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketBootstrapContainer_To_upstreamv1beta1_BottlerocketBootstrapContainer(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta1_BottlerocketControl_To_v1beta1_BottlerocketControl(in *BottlerocketControl, out *v1beta1.BottlerocketControl, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta1_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_upstreamv1beta1_BottlerocketControl_To_v1beta1_BottlerocketControl is an autogenerated conversion function. ++func Convert_upstreamv1beta1_BottlerocketControl_To_v1beta1_BottlerocketControl(in *BottlerocketControl, out *v1beta1.BottlerocketControl, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_BottlerocketControl_To_v1beta1_BottlerocketControl(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketControl_To_upstreamv1beta1_BottlerocketControl(in *v1beta1.BottlerocketControl, out *BottlerocketControl, s conversion.Scope) error { ++ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketControl_To_upstreamv1beta1_BottlerocketControl is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketControl_To_upstreamv1beta1_BottlerocketControl(in *v1beta1.BottlerocketControl, out *BottlerocketControl, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketControl_To_upstreamv1beta1_BottlerocketControl(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta1_BottlerocketHostContainer_To_v1beta1_BottlerocketHostContainer(in *BottlerocketHostContainer, out *v1beta1.BottlerocketHostContainer, s conversion.Scope) error { ++ out.Name = in.Name ++ out.Superpowered = in.Superpowered ++ if err := Convert_upstreamv1beta1_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ out.UserData = in.UserData ++ return nil ++} ++ ++// Convert_upstreamv1beta1_BottlerocketHostContainer_To_v1beta1_BottlerocketHostContainer is an autogenerated conversion function. ++func Convert_upstreamv1beta1_BottlerocketHostContainer_To_v1beta1_BottlerocketHostContainer(in *BottlerocketHostContainer, out *v1beta1.BottlerocketHostContainer, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_BottlerocketHostContainer_To_v1beta1_BottlerocketHostContainer(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketHostContainer_To_upstreamv1beta1_BottlerocketHostContainer(in *v1beta1.BottlerocketHostContainer, out *BottlerocketHostContainer, s conversion.Scope) error { ++ out.Name = in.Name ++ out.Superpowered = in.Superpowered ++ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ out.UserData = in.UserData ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketHostContainer_To_upstreamv1beta1_BottlerocketHostContainer is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketHostContainer_To_upstreamv1beta1_BottlerocketHostContainer(in *v1beta1.BottlerocketHostContainer, out *BottlerocketHostContainer, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketHostContainer_To_upstreamv1beta1_BottlerocketHostContainer(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta1_BottlerocketKernelSettings_To_v1beta1_BottlerocketKernelSettings(in *BottlerocketKernelSettings, out *v1beta1.BottlerocketKernelSettings, s conversion.Scope) error { ++ out.SysctlSettings = *(*map[string]string)(unsafe.Pointer(&in.SysctlSettings)) ++ return nil ++} ++ ++// Convert_upstreamv1beta1_BottlerocketKernelSettings_To_v1beta1_BottlerocketKernelSettings is an autogenerated conversion function. ++func Convert_upstreamv1beta1_BottlerocketKernelSettings_To_v1beta1_BottlerocketKernelSettings(in *BottlerocketKernelSettings, out *v1beta1.BottlerocketKernelSettings, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_BottlerocketKernelSettings_To_v1beta1_BottlerocketKernelSettings(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketKernelSettings_To_upstreamv1beta1_BottlerocketKernelSettings(in *v1beta1.BottlerocketKernelSettings, out *BottlerocketKernelSettings, s conversion.Scope) error { ++ out.SysctlSettings = *(*map[string]string)(unsafe.Pointer(&in.SysctlSettings)) ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketKernelSettings_To_upstreamv1beta1_BottlerocketKernelSettings is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketKernelSettings_To_upstreamv1beta1_BottlerocketKernelSettings(in *v1beta1.BottlerocketKernelSettings, out *BottlerocketKernelSettings, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketKernelSettings_To_upstreamv1beta1_BottlerocketKernelSettings(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta1_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings(in *BottlerocketKubernetesSettings, out *v1beta1.BottlerocketKubernetesSettings, s conversion.Scope) error { ++ out.MaxPods = in.MaxPods ++ out.AllowedUnsafeSysctls = *(*[]string)(unsafe.Pointer(&in.AllowedUnsafeSysctls)) ++ out.ClusterDNSIPs = *(*[]string)(unsafe.Pointer(&in.ClusterDNSIPs)) ++ return nil ++} ++ ++// Convert_upstreamv1beta1_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings is an autogenerated conversion function. ++func Convert_upstreamv1beta1_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings(in *BottlerocketKubernetesSettings, out *v1beta1.BottlerocketKubernetesSettings, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_BottlerocketKubernetesSettings_To_v1beta1_BottlerocketKubernetesSettings(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketKubernetesSettings_To_upstreamv1beta1_BottlerocketKubernetesSettings(in *v1beta1.BottlerocketKubernetesSettings, out *BottlerocketKubernetesSettings, s conversion.Scope) error { ++ out.MaxPods = in.MaxPods ++ out.AllowedUnsafeSysctls = *(*[]string)(unsafe.Pointer(&in.AllowedUnsafeSysctls)) ++ out.ClusterDNSIPs = *(*[]string)(unsafe.Pointer(&in.ClusterDNSIPs)) ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketKubernetesSettings_To_upstreamv1beta1_BottlerocketKubernetesSettings is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketKubernetesSettings_To_upstreamv1beta1_BottlerocketKubernetesSettings(in *v1beta1.BottlerocketKubernetesSettings, out *BottlerocketKubernetesSettings, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketKubernetesSettings_To_upstreamv1beta1_BottlerocketKubernetesSettings(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta1_BottlerocketSettings_To_v1beta1_BottlerocketSettings(in *BottlerocketSettings, out *v1beta1.BottlerocketSettings, s conversion.Scope) error { ++ out.Kubernetes = (*v1beta1.BottlerocketKubernetesSettings)(unsafe.Pointer(in.Kubernetes)) ++ out.Kernel = (*v1beta1.BottlerocketKernelSettings)(unsafe.Pointer(in.Kernel)) ++ return nil ++} ++ ++// Convert_upstreamv1beta1_BottlerocketSettings_To_v1beta1_BottlerocketSettings is an autogenerated conversion function. ++func Convert_upstreamv1beta1_BottlerocketSettings_To_v1beta1_BottlerocketSettings(in *BottlerocketSettings, out *v1beta1.BottlerocketSettings, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_BottlerocketSettings_To_v1beta1_BottlerocketSettings(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketSettings_To_upstreamv1beta1_BottlerocketSettings(in *v1beta1.BottlerocketSettings, out *BottlerocketSettings, s conversion.Scope) error { ++ out.Kubernetes = (*BottlerocketKubernetesSettings)(unsafe.Pointer(in.Kubernetes)) ++ out.Kernel = (*BottlerocketKernelSettings)(unsafe.Pointer(in.Kernel)) ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketSettings_To_upstreamv1beta1_BottlerocketSettings is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketSettings_To_upstreamv1beta1_BottlerocketSettings(in *v1beta1.BottlerocketSettings, out *BottlerocketSettings, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketSettings_To_upstreamv1beta1_BottlerocketSettings(in, out, s) ++} ++ + func autoConvert_upstreamv1beta1_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *ClusterConfiguration, out *v1beta1.ClusterConfiguration, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta1_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta1_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta1_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(&in.BottlerocketAdmin, &out.BottlerocketAdmin, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta1_BottlerocketControl_To_v1beta1_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta1_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta1_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_upstreamv1beta1_Etcd_To_v1beta1_Etcd(&in.Etcd, &out.Etcd, s); err != nil { + return err + } +@@ -405,10 +733,31 @@ func autoConvert_upstreamv1beta1_ClusterConfiguration_To_v1beta1_ClusterConfigur + // WARNING: in.UseHyperKubeImage requires manual conversion: does not exist in peer-type + out.FeatureGates = *(*map[string]bool)(unsafe.Pointer(&in.FeatureGates)) + out.ClusterName = in.ClusterName ++ out.BottlerocketHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) ++ out.BottlerocketCustomBootstrapContainers = *(*[]v1beta1.BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) ++ out.Bottlerocket = (*v1beta1.BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) + return nil + } + + func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta1_ClusterConfiguration(in *v1beta1.ClusterConfiguration, out *ClusterConfiguration, s conversion.Scope) error { ++ if err := Convert_v1beta1_Pause_To_upstreamv1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketAdmin_To_upstreamv1beta1_BottlerocketAdmin(&in.BottlerocketAdmin, &out.BottlerocketAdmin, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketControl_To_upstreamv1beta1_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_v1beta1_Etcd_To_upstreamv1beta1_Etcd(&in.Etcd, &out.Etcd, s); err != nil { + return err + } +@@ -433,6 +782,9 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta1_ClusterConfigur + out.ImageRepository = in.ImageRepository + out.FeatureGates = *(*map[string]bool)(unsafe.Pointer(&in.FeatureGates)) + out.ClusterName = in.ClusterName ++ out.BottlerocketHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) ++ out.BottlerocketCustomBootstrapContainers = *(*[]BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) ++ out.Bottlerocket = (*BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) + return nil + } + +@@ -677,6 +1029,24 @@ func autoConvert_v1beta1_InitConfiguration_To_upstreamv1beta1_InitConfiguration( + } + + func autoConvert_upstreamv1beta1_JoinConfiguration_To_v1beta1_JoinConfiguration(in *JoinConfiguration, out *v1beta1.JoinConfiguration, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta1_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta1_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta1_BottlerocketAdmin_To_v1beta1_BottlerocketAdmin(&in.BottlerocketAdmin, &out.BottlerocketAdmin, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta1_BottlerocketControl_To_v1beta1_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta1_ProxyConfiguration_To_v1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_upstreamv1beta1_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_upstreamv1beta1_NodeRegistrationOptions_To_v1beta1_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { + return err + } +@@ -685,6 +1055,9 @@ func autoConvert_upstreamv1beta1_JoinConfiguration_To_v1beta1_JoinConfiguration( + return err + } + out.ControlPlane = (*v1beta1.JoinControlPlane)(unsafe.Pointer(in.ControlPlane)) ++ out.BottlerocketCustomHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) ++ out.BottlerocketCustomBootstrapContainers = *(*[]v1beta1.BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) ++ out.Bottlerocket = (*v1beta1.BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) + return nil + } + +@@ -694,6 +1067,24 @@ func Convert_upstreamv1beta1_JoinConfiguration_To_v1beta1_JoinConfiguration(in * + } + + func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta1_JoinConfiguration(in *v1beta1.JoinConfiguration, out *JoinConfiguration, s conversion.Scope) error { ++ if err := Convert_v1beta1_Pause_To_upstreamv1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketBootstrap_To_upstreamv1beta1_BottlerocketBootstrap(&in.BottlerocketBootstrap, &out.BottlerocketBootstrap, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketAdmin_To_upstreamv1beta1_BottlerocketAdmin(&in.BottlerocketAdmin, &out.BottlerocketAdmin, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_BottlerocketControl_To_upstreamv1beta1_BottlerocketControl(&in.BottlerocketControl, &out.BottlerocketControl, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta1_ProxyConfiguration(&in.Proxy, &out.Proxy, s); err != nil { ++ return err ++ } ++ if err := Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta1_RegistryMirrorConfiguration(&in.RegistryMirror, &out.RegistryMirror, s); err != nil { ++ return err ++ } + if err := Convert_v1beta1_NodeRegistrationOptions_To_upstreamv1beta1_NodeRegistrationOptions(&in.NodeRegistration, &out.NodeRegistration, s); err != nil { + return err + } +@@ -704,6 +1095,9 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta1_JoinConfiguration( + out.ControlPlane = (*JoinControlPlane)(unsafe.Pointer(in.ControlPlane)) + // WARNING: in.SkipPhases requires manual conversion: does not exist in peer-type + // WARNING: in.Patches requires manual conversion: does not exist in peer-type ++ out.BottlerocketCustomHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) ++ out.BottlerocketCustomBootstrapContainers = *(*[]BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) ++ out.Bottlerocket = (*BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) + return nil + } + +@@ -809,3 +1203,71 @@ func autoConvert_v1beta1_NodeRegistrationOptions_To_upstreamv1beta1_NodeRegistra + // WARNING: in.ImagePullPolicy requires manual conversion: does not exist in peer-type + return nil + } ++ ++func autoConvert_upstreamv1beta1_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { ++ if err := Convert_upstreamv1beta1_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_upstreamv1beta1_Pause_To_v1beta1_Pause is an autogenerated conversion function. ++func Convert_upstreamv1beta1_Pause_To_v1beta1_Pause(in *Pause, out *v1beta1.Pause, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_Pause_To_v1beta1_Pause(in, out, s) ++} ++ ++func autoConvert_v1beta1_Pause_To_upstreamv1beta1_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { ++ if err := Convert_v1beta1_ImageMeta_To_upstreamv1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { ++ return err ++ } ++ return nil ++} ++ ++// Convert_v1beta1_Pause_To_upstreamv1beta1_Pause is an autogenerated conversion function. ++func Convert_v1beta1_Pause_To_upstreamv1beta1_Pause(in *v1beta1.Pause, out *Pause, s conversion.Scope) error { ++ return autoConvert_v1beta1_Pause_To_upstreamv1beta1_Pause(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta1_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { ++ out.HTTPSProxy = in.HTTPSProxy ++ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) ++ return nil ++} ++ ++// Convert_upstreamv1beta1_ProxyConfiguration_To_v1beta1_ProxyConfiguration is an autogenerated conversion function. ++func Convert_upstreamv1beta1_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in *ProxyConfiguration, out *v1beta1.ProxyConfiguration, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_ProxyConfiguration_To_v1beta1_ProxyConfiguration(in, out, s) ++} ++ ++func autoConvert_v1beta1_ProxyConfiguration_To_upstreamv1beta1_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { ++ out.HTTPSProxy = in.HTTPSProxy ++ out.NoProxy = *(*[]string)(unsafe.Pointer(&in.NoProxy)) ++ return nil ++} ++ ++// Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta1_ProxyConfiguration is an autogenerated conversion function. ++func Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta1_ProxyConfiguration(in *v1beta1.ProxyConfiguration, out *ProxyConfiguration, s conversion.Scope) error { ++ return autoConvert_v1beta1_ProxyConfiguration_To_upstreamv1beta1_ProxyConfiguration(in, out, s) ++} ++ ++func autoConvert_upstreamv1beta1_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { ++ out.Endpoint = in.Endpoint ++ out.CACert = in.CACert ++ return nil ++} ++ ++// Convert_upstreamv1beta1_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration is an autogenerated conversion function. ++func Convert_upstreamv1beta1_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in, out, s) ++} ++ ++func autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta1_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { ++ out.Endpoint = in.Endpoint ++ out.CACert = in.CACert ++ return nil ++} ++ ++// Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta1_RegistryMirrorConfiguration is an autogenerated conversion function. ++func Convert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta1_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { ++ return autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta1_RegistryMirrorConfiguration(in, out, s) ++} +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +index c28f28c4c..50d010408 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +@@ -221,6 +221,28 @@ func (in *BottlerocketHostContainer) DeepCopy() *BottlerocketHostContainer { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketKernelSettings) DeepCopyInto(out *BottlerocketKernelSettings) { ++ *out = *in ++ if in.SysctlSettings != nil { ++ in, out := &in.SysctlSettings, &out.SysctlSettings ++ *out = make(map[string]string, len(*in)) ++ for key, val := range *in { ++ (*out)[key] = val ++ } ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketKernelSettings. ++func (in *BottlerocketKernelSettings) DeepCopy() *BottlerocketKernelSettings { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketKernelSettings) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketKubernetesSettings) DeepCopyInto(out *BottlerocketKubernetesSettings) { + *out = *in +@@ -254,6 +276,11 @@ func (in *BottlerocketSettings) DeepCopyInto(out *BottlerocketSettings) { + *out = new(BottlerocketKubernetesSettings) + (*in).DeepCopyInto(*out) + } ++ if in.Kernel != nil { ++ in, out := &in.Kernel, &out.Kernel ++ *out = new(BottlerocketKernelSettings) ++ (*in).DeepCopyInto(*out) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketSettings. +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +index cda7db3f5..905f4575c 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +@@ -182,6 +182,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -965,6 +976,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -1734,6 +1756,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -2514,6 +2547,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -3367,6 +3411,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -4220,6 +4275,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional kernel ++ settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel sysctl ++ settings to set for bottlerocket nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +index 055b51899..b3ca9161f 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +@@ -130,6 +130,18 @@ spec: + certain bottlerocket settings. This is only for + bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional ++ kernel settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel ++ sysctl settings to set for bottlerocket ++ nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -963,6 +975,18 @@ spec: + certain bottlerocket settings. This is only for + bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional ++ kernel settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel ++ sysctl settings to set for bottlerocket ++ nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -1753,6 +1777,18 @@ spec: + certain bottlerocket settings. This is only for + bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional ++ kernel settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel ++ sysctl settings to set for bottlerocket ++ nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +@@ -2665,6 +2701,18 @@ spec: + certain bottlerocket settings. This is only for + bottlerocket. + properties: ++ kernel: ++ description: KernelSettings contains additional ++ kernel settings for Bottlerocket. ++ properties: ++ sysctlSettings: ++ additionalProperties: ++ type: string ++ description: SysctlSettings defines the kernel ++ sysctl settings to set for bottlerocket ++ nodes. ++ type: object ++ type: object + kubernetes: + description: Kubernetes holds the kubernetes settings + for bottlerocket nodes. +-- +2.42.0 + diff --git a/projects/kubernetes-sigs/cluster-api/patches/0027-add-boot-kernel-settings-for-BR.patch b/projects/kubernetes-sigs/cluster-api/patches/0027-add-boot-kernel-settings-for-BR.patch new file mode 100644 index 0000000000..b4cff00bff --- /dev/null +++ b/projects/kubernetes-sigs/cluster-api/patches/0027-add-boot-kernel-settings-for-BR.patch @@ -0,0 +1,998 @@ +From 18ad3d3b2795b06630ddddc47422fc9192d9279d Mon Sep 17 00:00:00 2001 +From: Ahree Hong +Date: Thu, 23 Mar 2023 01:51:16 -0700 +Subject: [PATCH 27/40] add boot kernel settings for BR + +Signed-off-by: Ahree Hong +--- + .../kubeadm/api/v1alpha4/kubeadm_types.go | 8 +++ + .../api/v1alpha4/zz_generated.conversion.go | 32 +++++++++ + .../api/v1alpha4/zz_generated.deepcopy.go | 36 ++++++++++ + .../kubeadm/api/v1beta1/kubeadm_types.go | 8 +++ + .../api/v1beta1/zz_generated.deepcopy.go | 36 ++++++++++ + ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 66 +++++++++++++++++++ + ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 66 +++++++++++++++++++ + .../internal/bottlerocket/bootstrap.go | 13 ++++ + .../internal/bottlerocket/bootstrap_test.go | 57 ++++++++++++++++ + .../internal/bottlerocket/bottlerocket.go | 24 +++++++ + .../kubeadm/types/upstreamv1beta1/types.go | 8 +++ + .../zz_generated.conversion.go | 32 +++++++++ + .../upstreamv1beta1/zz_generated.deepcopy.go | 36 ++++++++++ + ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 66 +++++++++++++++++++ + ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 44 +++++++++++++ + .../machine/machine_controller_phases.go | 5 +- + 16 files changed, 535 insertions(+), 2 deletions(-) + +diff --git a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +index c00ea0a53..010efa948 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +@@ -182,6 +182,9 @@ type BottlerocketSettings struct { + // KernelSettings contains additional kernel settings for Bottlerocket. + // +optional + Kernel *BottlerocketKernelSettings `json:"kernel,omitempty"` ++ ++ // Boot holds the boot-related settings for bottlerocket nodes ++ Boot *BottlerocketBootSettings `json:"boot,omitempty"` + } + + // BottlerocketKubernetesSettings holds the settings for kubernetes on bottlerocket nodes. +@@ -203,6 +206,11 @@ type BottlerocketKernelSettings struct { + SysctlSettings map[string]string `json:"sysctlSettings,omitempty"` + } + ++// BottlerocketBootSettings holds the boot-related settings for bottlerocket nodes. ++type BottlerocketBootSettings struct { ++ BootKernelParameters map[string][]string `json:"bootKernelParameters,omitempty"` ++} ++ + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. + // This setting is ONLY for bottlerocket nodes, as this needs to be set pre-boot time along with user-data + type Pause struct { +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +index 70c06fcf3..8f36b6a13 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +@@ -100,6 +100,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketBootSettings)(nil), (*v1beta1.BottlerocketBootSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_BottlerocketBootSettings_To_v1beta1_BottlerocketBootSettings(a.(*BottlerocketBootSettings), b.(*v1beta1.BottlerocketBootSettings), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketBootSettings)(nil), (*BottlerocketBootSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketBootSettings_To_v1alpha4_BottlerocketBootSettings(a.(*v1beta1.BottlerocketBootSettings), b.(*BottlerocketBootSettings), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrap)(nil), (*v1beta1.BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(a.(*BottlerocketBootstrap), b.(*v1beta1.BottlerocketBootstrap), scope) + }); err != nil { +@@ -675,6 +685,26 @@ func Convert_v1beta1_BottlerocketAdmin_To_v1alpha4_BottlerocketAdmin(in *v1beta1 + return autoConvert_v1beta1_BottlerocketAdmin_To_v1alpha4_BottlerocketAdmin(in, out, s) + } + ++func autoConvert_v1alpha4_BottlerocketBootSettings_To_v1beta1_BottlerocketBootSettings(in *BottlerocketBootSettings, out *v1beta1.BottlerocketBootSettings, s conversion.Scope) error { ++ out.BootKernelParameters = *(*map[string][]string)(unsafe.Pointer(&in.BootKernelParameters)) ++ return nil ++} ++ ++// Convert_v1alpha4_BottlerocketBootSettings_To_v1beta1_BottlerocketBootSettings is an autogenerated conversion function. ++func Convert_v1alpha4_BottlerocketBootSettings_To_v1beta1_BottlerocketBootSettings(in *BottlerocketBootSettings, out *v1beta1.BottlerocketBootSettings, s conversion.Scope) error { ++ return autoConvert_v1alpha4_BottlerocketBootSettings_To_v1beta1_BottlerocketBootSettings(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketBootSettings_To_v1alpha4_BottlerocketBootSettings(in *v1beta1.BottlerocketBootSettings, out *BottlerocketBootSettings, s conversion.Scope) error { ++ out.BootKernelParameters = *(*map[string][]string)(unsafe.Pointer(&in.BootKernelParameters)) ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketBootSettings_To_v1alpha4_BottlerocketBootSettings is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketBootSettings_To_v1alpha4_BottlerocketBootSettings(in *v1beta1.BottlerocketBootSettings, out *BottlerocketBootSettings, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketBootSettings_To_v1alpha4_BottlerocketBootSettings(in, out, s) ++} ++ + func autoConvert_v1alpha4_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { + if err := Convert_v1alpha4_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { + return err +@@ -832,6 +862,7 @@ func Convert_v1beta1_BottlerocketKubernetesSettings_To_v1alpha4_BottlerocketKube + func autoConvert_v1alpha4_BottlerocketSettings_To_v1beta1_BottlerocketSettings(in *BottlerocketSettings, out *v1beta1.BottlerocketSettings, s conversion.Scope) error { + out.Kubernetes = (*v1beta1.BottlerocketKubernetesSettings)(unsafe.Pointer(in.Kubernetes)) + out.Kernel = (*v1beta1.BottlerocketKernelSettings)(unsafe.Pointer(in.Kernel)) ++ out.Boot = (*v1beta1.BottlerocketBootSettings)(unsafe.Pointer(in.Boot)) + return nil + } + +@@ -843,6 +874,7 @@ func Convert_v1alpha4_BottlerocketSettings_To_v1beta1_BottlerocketSettings(in *B + func autoConvert_v1beta1_BottlerocketSettings_To_v1alpha4_BottlerocketSettings(in *v1beta1.BottlerocketSettings, out *BottlerocketSettings, s conversion.Scope) error { + out.Kubernetes = (*BottlerocketKubernetesSettings)(unsafe.Pointer(in.Kubernetes)) + out.Kernel = (*BottlerocketKernelSettings)(unsafe.Pointer(in.Kernel)) ++ out.Boot = (*BottlerocketBootSettings)(unsafe.Pointer(in.Boot)) + return nil + } + +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +index 44bbe16ce..f8d8004c0 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +@@ -158,6 +158,37 @@ func (in *BottlerocketAdmin) DeepCopy() *BottlerocketAdmin { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketBootSettings) DeepCopyInto(out *BottlerocketBootSettings) { ++ *out = *in ++ if in.BootKernelParameters != nil { ++ in, out := &in.BootKernelParameters, &out.BootKernelParameters ++ *out = make(map[string][]string, len(*in)) ++ for key, val := range *in { ++ var outVal []string ++ if val == nil { ++ (*out)[key] = nil ++ } else { ++ inVal := (*in)[key] ++ in, out := &inVal, &outVal ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++ (*out)[key] = outVal ++ } ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootSettings. ++func (in *BottlerocketBootSettings) DeepCopy() *BottlerocketBootSettings { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketBootSettings) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { + *out = *in +@@ -282,6 +313,11 @@ func (in *BottlerocketSettings) DeepCopyInto(out *BottlerocketSettings) { + *out = new(BottlerocketKernelSettings) + (*in).DeepCopyInto(*out) + } ++ if in.Boot != nil { ++ in, out := &in.Boot, &out.Boot ++ *out = new(BottlerocketBootSettings) ++ (*in).DeepCopyInto(*out) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketSettings. +diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +index c97ef8604..434d2c088 100644 +--- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +@@ -201,6 +201,9 @@ type BottlerocketSettings struct { + // KernelSettings contains additional kernel settings for Bottlerocket. + // +optional + Kernel *BottlerocketKernelSettings `json:"kernel,omitempty"` ++ ++ // Boot holds the boot-related settings for bottlerocket nodes ++ Boot *BottlerocketBootSettings `json:"boot,omitempty"` + } + + // BottlerocketKubernetesSettings holds the settings for kubernetes on bottlerocket nodes. +@@ -222,6 +225,11 @@ type BottlerocketKernelSettings struct { + SysctlSettings map[string]string `json:"sysctlSettings,omitempty"` + } + ++// BottlerocketBootSettings holds the boot-related settings for bottlerocket nodes. ++type BottlerocketBootSettings struct { ++ BootKernelParameters map[string][]string `json:"bootKernelParameters,omitempty"` ++} ++ + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. + // This setting is ONLY for bottlerocket nodes, as this needs to be set pre-boot time along with user-data + type Pause struct { +diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +index d335a35b1..c89d4aa1f 100644 +--- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +@@ -158,6 +158,37 @@ func (in *BottlerocketAdmin) DeepCopy() *BottlerocketAdmin { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketBootSettings) DeepCopyInto(out *BottlerocketBootSettings) { ++ *out = *in ++ if in.BootKernelParameters != nil { ++ in, out := &in.BootKernelParameters, &out.BootKernelParameters ++ *out = make(map[string][]string, len(*in)) ++ for key, val := range *in { ++ var outVal []string ++ if val == nil { ++ (*out)[key] = nil ++ } else { ++ inVal := (*in)[key] ++ in, out := &inVal, &outVal ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++ (*out)[key] = outVal ++ } ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootSettings. ++func (in *BottlerocketBootSettings) DeepCopy() *BottlerocketBootSettings { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketBootSettings) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { + *out = *in +@@ -282,6 +313,11 @@ func (in *BottlerocketSettings) DeepCopyInto(out *BottlerocketSettings) { + *out = new(BottlerocketKernelSettings) + (*in).DeepCopyInto(*out) + } ++ if in.Boot != nil { ++ in, out := &in.Boot, &out.Boot ++ *out = new(BottlerocketBootSettings) ++ (*in).DeepCopyInto(*out) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketSettings. +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +index 13eab82cd..0591279db 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +@@ -107,6 +107,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for bottlerocket ++ nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel settings + for Bottlerocket. +@@ -871,6 +882,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for bottlerocket ++ nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel settings + for Bottlerocket. +@@ -1514,6 +1536,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for bottlerocket ++ nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel settings + for Bottlerocket. +@@ -2274,6 +2307,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for bottlerocket ++ nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel settings + for Bottlerocket. +@@ -2915,6 +2959,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for bottlerocket ++ nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel settings + for Bottlerocket. +@@ -3744,6 +3799,17 @@ spec: + description: Bottlerocket holds configuration for certain bottlerocket + settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for bottlerocket ++ nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel settings + for Bottlerocket. +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +index 02cc4c0ed..75574d5e7 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +@@ -115,6 +115,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings ++ for bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +@@ -926,6 +937,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings ++ for bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +@@ -1536,6 +1558,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings ++ for bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +@@ -2345,6 +2378,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings ++ for bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +@@ -2978,6 +3022,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings ++ for bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +@@ -3864,6 +3919,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings ++ for bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +index a23a43668..901db1cb7 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +@@ -119,6 +119,15 @@ time-servers = [{{stringsJoin .NTPServers ", " }}] + [settings.kernel.sysctl] + {{.SysctlSettings}} + {{- end -}} ++` ++ ++ bootSettingsTemplate = `{{ define "bootSettings" -}} ++[settings.boot] ++reboot-to-reconcile = true ++ ++[settings.boot.kernel-parameters] ++{{.BootKernel}} ++{{- end -}} + ` + + bottlerocketNodeInitSettingsTemplate = `{{template "hostContainerSlice" .}} +@@ -159,5 +168,9 @@ time-servers = [{{stringsJoin .NTPServers ", " }}] + {{- if (ne .SysctlSettings "")}} + {{template "sysctlSettingsTemplate" .}} + {{- end -}} ++ ++{{- if .BootKernel}} ++{{template "bootSettings" .}} ++{{- end -}} + ` + ) +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +index fdc60204d..5846524be 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +@@ -279,6 +279,36 @@ hostname = "hostname" + [settings.kernel.sysctl] + "foo" = "bar" + "abc" = "def" ++` ++ ++ BootSettingsUserData = ` ++[settings.host-containers.admin] ++enabled = true ++superpowered = true ++source = "ADMIN_REPO:ADMIN_TAG" ++user-data = "CnsKCSJzc2giOiB7CgkJImF1dGhvcml6ZWQta2V5cyI6IFsic3NoLXJzYSBBQUEuLi4iXQoJfQp9" ++[settings.host-containers.kubeadm-bootstrap] ++enabled = true ++superpowered = true ++source = "BOOTSTRAP_REPO:BOOTSTRAP_TAG" ++user-data = "Qk9UVExFUk9DS0VUX0JPT1RTVFJBUF9VU0VSREFUQQ==" ++ ++[settings.kubernetes] ++cluster-domain = "cluster.local" ++standalone-mode = true ++authentication-mode = "tls" ++server-tls-bootstrap = false ++pod-infra-container-image = "PAUSE_REPO:PAUSE_TAG" ++provider-id = "PROVIDERID" ++ ++[settings.network] ++hostname = "hostname" ++[settings.boot] ++reboot-to-reconcile = true ++ ++[settings.boot.kernel-parameters] ++"abc" = ["def","123"] ++"foo" = ["bar"] + ` + ) + +@@ -513,10 +543,37 @@ func TestGetBottlerocketNodeUserData(t *testing.T) { + }, + output: kernelSettingsUserData, + }, ++ { ++ name: "with boot settings", ++ config: &BottlerocketConfig{ ++ BottlerocketAdmin: brAdmin, ++ BottlerocketBootstrap: brBootstrap, ++ Hostname: hostname, ++ Pause: pause, ++ KubeletExtraArgs: map[string]string{ ++ "provider-id": "PROVIDERID", ++ }, ++ BottlerocketSettings: &bootstrapv1.BottlerocketSettings{ ++ Boot: &bootstrapv1.BottlerocketBootSettings{ ++ BootKernelParameters: map[string][]string{ ++ "abc": { ++ "def", ++ "123", ++ }, ++ "foo": { ++ "bar", ++ }, ++ }, ++ }, ++ }, ++ }, ++ output: BootSettingsUserData, ++ }, + } + for _, testcase := range testcases { + t.Run(testcase.name, func(t *testing.T) { + b, err := getBottlerocketNodeUserData(brBootstrapUserdata, users, testcase.config) ++ println(string(b)) + g.Expect(err).NotTo(HaveOccurred()) + g.Expect(string(b)).To(Equal(testcase.output)) + }) +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +index afd854f1c..7b7131829 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +@@ -57,6 +57,7 @@ type BottlerocketSettingsInput struct { + AllowedUnsafeSysctls []string + ClusterDNSIPs []string + MaxPods int ++ BootKernel string + HostContainers []bootstrapv1.BottlerocketHostContainer + BootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer + SysctlSettings string +@@ -160,6 +161,9 @@ func generateNodeUserData(kind string, tpl string, data interface{}) ([]byte, er + if _, err := tm.Parse(sysctlSettingsTemplate); err != nil { + return nil, errors.Wrapf(err, "failed to parse sysctl settings %s template", kind) + } ++ if _, err := tm.Parse(bootSettingsTemplate); err != nil { ++ return nil, errors.Wrapf(err, "failed to parse boot settings %s template", kind) ++ } + t, err := tm.Parse(tpl) + if err != nil { + return nil, errors.Wrapf(err, "failed to parse %s template", kind) +@@ -257,6 +261,10 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot + bottlerocketInput.SysctlSettings = parseSysctlSettings(config.BottlerocketSettings.Kernel.SysctlSettings) + } + ++ if config.BottlerocketSettings.Boot != nil { ++ bottlerocketInput.BootKernel = parseBootSettings(config.BottlerocketSettings.Boot.BootKernelParameters) ++ } ++ + } + + return generateNodeUserData("InitBottlerocketNode", bottlerocketNodeInitSettingsTemplate, bottlerocketInput) +@@ -315,6 +323,22 @@ func parseSysctlSettings(sysctlSettings map[string]string) string { + return sysctlSettingsToml + } + ++func parseBootSettings(bootSettings map[string][]string) string { ++ bootSettingsToml := "" ++ for key, value := range bootSettings { ++ var values []string ++ if len(value) != 0 { ++ for _, val := range value { ++ quotedVal := "\"" + val + "\"" ++ values = append(values, quotedVal) ++ } ++ } ++ keyVal := strings.Join(values, ",") ++ bootSettingsToml += fmt.Sprintf("\"%v\" = [%v]\n", key, keyVal) ++ } ++ return bootSettingsToml ++} ++ + // Parses through all the users and return list of all user's authorized ssh keys + func getAllAuthorizedKeys(users []bootstrapv1.User) string { + var sshAuthorizedKeys []string +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/types.go b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +index 4563d15de..1b7ce57fe 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/types.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +@@ -180,6 +180,9 @@ type BottlerocketSettings struct { + // KernelSettings contains additional kernel settings for Bottlerocket. + // +optional + Kernel *BottlerocketKernelSettings `json:"kernel,omitempty"` ++ ++ // Boot holds the boot-related settings for bottlerocket nodes ++ Boot *BottlerocketBootSettings `json:"boot,omitempty"` + } + + // BottlerocketKubernetesSettings holds the settings for kubernetes on bottlerocket nodes. +@@ -201,6 +204,11 @@ type BottlerocketKernelSettings struct { + SysctlSettings map[string]string `json:"sysctlSettings,omitempty"` + } + ++// BottlerocketBootSettings holds the boot-related settings for bottlerocket nodes. ++type BottlerocketBootSettings struct { ++ BootKernelParameters map[string][]string `json:"bootKernelParameters,omitempty"` ++} ++ + // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. + // This setting is ONLY for bottlerocket nodes, as this needs to be set pre-boot time along with user-data + type Pause struct { +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go +index 905b58372..5cef55e28 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go +@@ -98,6 +98,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*BottlerocketBootSettings)(nil), (*v1beta1.BottlerocketBootSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_BottlerocketBootSettings_To_v1beta1_BottlerocketBootSettings(a.(*BottlerocketBootSettings), b.(*v1beta1.BottlerocketBootSettings), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.BottlerocketBootSettings)(nil), (*BottlerocketBootSettings)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_BottlerocketBootSettings_To_upstreamv1beta1_BottlerocketBootSettings(a.(*v1beta1.BottlerocketBootSettings), b.(*BottlerocketBootSettings), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*BottlerocketBootstrap)(nil), (*v1beta1.BottlerocketBootstrap)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_upstreamv1beta1_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(a.(*BottlerocketBootstrap), b.(*v1beta1.BottlerocketBootstrap), scope) + }); err != nil { +@@ -513,6 +523,26 @@ func Convert_v1beta1_BottlerocketAdmin_To_upstreamv1beta1_BottlerocketAdmin(in * + return autoConvert_v1beta1_BottlerocketAdmin_To_upstreamv1beta1_BottlerocketAdmin(in, out, s) + } + ++func autoConvert_upstreamv1beta1_BottlerocketBootSettings_To_v1beta1_BottlerocketBootSettings(in *BottlerocketBootSettings, out *v1beta1.BottlerocketBootSettings, s conversion.Scope) error { ++ out.BootKernelParameters = *(*map[string][]string)(unsafe.Pointer(&in.BootKernelParameters)) ++ return nil ++} ++ ++// Convert_upstreamv1beta1_BottlerocketBootSettings_To_v1beta1_BottlerocketBootSettings is an autogenerated conversion function. ++func Convert_upstreamv1beta1_BottlerocketBootSettings_To_v1beta1_BottlerocketBootSettings(in *BottlerocketBootSettings, out *v1beta1.BottlerocketBootSettings, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_BottlerocketBootSettings_To_v1beta1_BottlerocketBootSettings(in, out, s) ++} ++ ++func autoConvert_v1beta1_BottlerocketBootSettings_To_upstreamv1beta1_BottlerocketBootSettings(in *v1beta1.BottlerocketBootSettings, out *BottlerocketBootSettings, s conversion.Scope) error { ++ out.BootKernelParameters = *(*map[string][]string)(unsafe.Pointer(&in.BootKernelParameters)) ++ return nil ++} ++ ++// Convert_v1beta1_BottlerocketBootSettings_To_upstreamv1beta1_BottlerocketBootSettings is an autogenerated conversion function. ++func Convert_v1beta1_BottlerocketBootSettings_To_upstreamv1beta1_BottlerocketBootSettings(in *v1beta1.BottlerocketBootSettings, out *BottlerocketBootSettings, s conversion.Scope) error { ++ return autoConvert_v1beta1_BottlerocketBootSettings_To_upstreamv1beta1_BottlerocketBootSettings(in, out, s) ++} ++ + func autoConvert_upstreamv1beta1_BottlerocketBootstrap_To_v1beta1_BottlerocketBootstrap(in *BottlerocketBootstrap, out *v1beta1.BottlerocketBootstrap, s conversion.Scope) error { + if err := Convert_upstreamv1beta1_ImageMeta_To_v1beta1_ImageMeta(&in.ImageMeta, &out.ImageMeta, s); err != nil { + return err +@@ -670,6 +700,7 @@ func Convert_v1beta1_BottlerocketKubernetesSettings_To_upstreamv1beta1_Bottleroc + func autoConvert_upstreamv1beta1_BottlerocketSettings_To_v1beta1_BottlerocketSettings(in *BottlerocketSettings, out *v1beta1.BottlerocketSettings, s conversion.Scope) error { + out.Kubernetes = (*v1beta1.BottlerocketKubernetesSettings)(unsafe.Pointer(in.Kubernetes)) + out.Kernel = (*v1beta1.BottlerocketKernelSettings)(unsafe.Pointer(in.Kernel)) ++ out.Boot = (*v1beta1.BottlerocketBootSettings)(unsafe.Pointer(in.Boot)) + return nil + } + +@@ -681,6 +712,7 @@ func Convert_upstreamv1beta1_BottlerocketSettings_To_v1beta1_BottlerocketSetting + func autoConvert_v1beta1_BottlerocketSettings_To_upstreamv1beta1_BottlerocketSettings(in *v1beta1.BottlerocketSettings, out *BottlerocketSettings, s conversion.Scope) error { + out.Kubernetes = (*BottlerocketKubernetesSettings)(unsafe.Pointer(in.Kubernetes)) + out.Kernel = (*BottlerocketKernelSettings)(unsafe.Pointer(in.Kernel)) ++ out.Boot = (*BottlerocketBootSettings)(unsafe.Pointer(in.Boot)) + return nil + } + +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +index 50d010408..2043410cf 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +@@ -157,6 +157,37 @@ func (in *BottlerocketAdmin) DeepCopy() *BottlerocketAdmin { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *BottlerocketBootSettings) DeepCopyInto(out *BottlerocketBootSettings) { ++ *out = *in ++ if in.BootKernelParameters != nil { ++ in, out := &in.BootKernelParameters, &out.BootKernelParameters ++ *out = make(map[string][]string, len(*in)) ++ for key, val := range *in { ++ var outVal []string ++ if val == nil { ++ (*out)[key] = nil ++ } else { ++ inVal := (*in)[key] ++ in, out := &inVal, &outVal ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++ (*out)[key] = outVal ++ } ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootSettings. ++func (in *BottlerocketBootSettings) DeepCopy() *BottlerocketBootSettings { ++ if in == nil { ++ return nil ++ } ++ out := new(BottlerocketBootSettings) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { + *out = *in +@@ -281,6 +312,11 @@ func (in *BottlerocketSettings) DeepCopyInto(out *BottlerocketSettings) { + *out = new(BottlerocketKernelSettings) + (*in).DeepCopyInto(*out) + } ++ if in.Boot != nil { ++ in, out := &in.Boot, &out.Boot ++ *out = new(BottlerocketBootSettings) ++ (*in).DeepCopyInto(*out) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketSettings. +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +index 905f4575c..fc37c0601 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +@@ -182,6 +182,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for ++ bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +@@ -976,6 +987,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for ++ bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +@@ -1756,6 +1778,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for ++ bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +@@ -2547,6 +2580,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for ++ bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +@@ -3411,6 +3455,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for ++ bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +@@ -4275,6 +4330,17 @@ spec: + description: Bottlerocket holds configuration for certain + bottlerocket settings. This is only for bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings for ++ bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional kernel + settings for Bottlerocket. +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +index b3ca9161f..c09d11044 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +@@ -130,6 +130,17 @@ spec: + certain bottlerocket settings. This is only for + bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings ++ for bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional + kernel settings for Bottlerocket. +@@ -975,6 +986,17 @@ spec: + certain bottlerocket settings. This is only for + bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings ++ for bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional + kernel settings for Bottlerocket. +@@ -1777,6 +1799,17 @@ spec: + certain bottlerocket settings. This is only for + bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings ++ for bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional + kernel settings for Bottlerocket. +@@ -2701,6 +2734,17 @@ spec: + certain bottlerocket settings. This is only for + bottlerocket. + properties: ++ boot: ++ description: Boot holds the boot-related settings ++ for bottlerocket nodes ++ properties: ++ bootKernelParameters: ++ additionalProperties: ++ items: ++ type: string ++ type: array ++ type: object ++ type: object + kernel: + description: KernelSettings contains additional + kernel settings for Bottlerocket. +diff --git a/internal/controllers/machine/machine_controller_phases.go b/internal/controllers/machine/machine_controller_phases.go +index 16febdda8..1da2d82ed 100644 +--- a/internal/controllers/machine/machine_controller_phases.go ++++ b/internal/controllers/machine/machine_controller_phases.go +@@ -19,9 +19,10 @@ package machine + import ( + "context" + "fmt" +- "sigs.k8s.io/controller-runtime/pkg/client" + "time" + ++ "sigs.k8s.io/controller-runtime/pkg/client" ++ + "github.com/pkg/errors" + corev1 "k8s.io/api/core/v1" + apierrors "k8s.io/apimachinery/pkg/api/errors" +@@ -392,7 +393,7 @@ func (r *Reconciler) reconcileInfrastructure(ctx context.Context, s *scope) (ctr + }, + }, + Data: map[string][]byte{ +- "address": []byte(machineIP), ++ "address": []byte(machineIP), + "clientUrls": []byte(fmt.Sprintf("https://%v:2379", machineIP)), + }, + Type: clusterv1.ClusterSecretType, +-- +2.42.0 + diff --git a/projects/kubernetes-sigs/cluster-api/patches/0030-Patch-haproxy-maxconn-value-to-avoid-ulimit-issue.patch b/projects/kubernetes-sigs/cluster-api/patches/0028-Patch-haproxy-maxconn-value-to-avoid-ulimit-issue.patch similarity index 88% rename from projects/kubernetes-sigs/cluster-api/patches/0030-Patch-haproxy-maxconn-value-to-avoid-ulimit-issue.patch rename to projects/kubernetes-sigs/cluster-api/patches/0028-Patch-haproxy-maxconn-value-to-avoid-ulimit-issue.patch index 1a9fa85de3..6a2c76a859 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0030-Patch-haproxy-maxconn-value-to-avoid-ulimit-issue.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0028-Patch-haproxy-maxconn-value-to-avoid-ulimit-issue.patch @@ -1,7 +1,7 @@ -From d023eacfe937292346e2445b14593bae82e8d0fc Mon Sep 17 00:00:00 2001 +From fe91076f036b835b3a5fb5aec3c75ca2f070f0af Mon Sep 17 00:00:00 2001 From: Jackson West Date: Sat, 6 May 2023 14:08:17 -0500 -Subject: [PATCH 30/40] Patch haproxy maxconn value to avoid ulimit issue +Subject: [PATCH 28/40] Patch haproxy maxconn value to avoid ulimit issue EKS-A uses haproxy 2.5 which errors if the maxconn value requires more FDs than allowed by the ulimit setting of docker. @@ -29,5 +29,5 @@ index 0e31f2a02..fc8bddf68 100644 resolvers docker nameserver dns 127.0.0.11:53 -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0028-add-br-kernel.sysctl-settings.patch b/projects/kubernetes-sigs/cluster-api/patches/0028-add-br-kernel.sysctl-settings.patch deleted file mode 100644 index b4321b9753..0000000000 --- a/projects/kubernetes-sigs/cluster-api/patches/0028-add-br-kernel.sysctl-settings.patch +++ /dev/null @@ -1,432 +0,0 @@ -From b0a793ffbce9f4554e1e37941eb59a9fdbe0db9b Mon Sep 17 00:00:00 2001 -From: Ahree Hong -Date: Tue, 7 Mar 2023 14:01:39 -0800 -Subject: [PATCH 28/40] add br kernel.sysctl settings - -Signed-off-by: Ahree Hong ---- - .../kubeadm/api/v1beta1/kubeadm_types.go | 10 ++++ - .../api/v1beta1/zz_generated.deepcopy.go | 27 +++++++++++ - ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 22 +++++++++ - ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 22 +++++++++ - .../internal/bottlerocket/bootstrap.go | 10 ++++ - .../internal/bottlerocket/bootstrap_test.go | 48 +++++++++++++++++++ - .../internal/bottlerocket/bottlerocket.go | 32 ++++++++++--- - .../api/v1alpha4/zz_generated.deepcopy.go | 2 +- - ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 22 +++++++++ - ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 24 ++++++++++ - 10 files changed, 211 insertions(+), 8 deletions(-) - -diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -index b3814c089..c97ef8604 100644 ---- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -+++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -@@ -197,6 +197,10 @@ type ClusterConfiguration struct { - type BottlerocketSettings struct { - // Kubernetes holds the kubernetes settings for bottlerocket nodes. - Kubernetes *BottlerocketKubernetesSettings `json:"kubernetes,omitempty"` -+ -+ // KernelSettings contains additional kernel settings for Bottlerocket. -+ // +optional -+ Kernel *BottlerocketKernelSettings `json:"kernel,omitempty"` - } - - // BottlerocketKubernetesSettings holds the settings for kubernetes on bottlerocket nodes. -@@ -212,6 +216,12 @@ type BottlerocketKubernetesSettings struct { - ClusterDNSIPs []string `json:"clusterDNSIPs,omitempty"` - } - -+// BottlerocketKernelSettings holds the kernel settings for bottlerocket nodes -+type BottlerocketKernelSettings struct { -+ // SysctlSettings defines the kernel sysctl settings to set for bottlerocket nodes. -+ SysctlSettings map[string]string `json:"sysctlSettings,omitempty"` -+} -+ - // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. - // This setting is ONLY for bottlerocket nodes, as this needs to be set pre-boot time along with user-data - type Pause struct { -diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -index 5e614f3cc..d335a35b1 100644 ---- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -+++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -@@ -222,6 +222,28 @@ func (in *BottlerocketHostContainer) DeepCopy() *BottlerocketHostContainer { - return out - } - -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *BottlerocketKernelSettings) DeepCopyInto(out *BottlerocketKernelSettings) { -+ *out = *in -+ if in.SysctlSettings != nil { -+ in, out := &in.SysctlSettings, &out.SysctlSettings -+ *out = make(map[string]string, len(*in)) -+ for key, val := range *in { -+ (*out)[key] = val -+ } -+ } -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketKernelSettings. -+func (in *BottlerocketKernelSettings) DeepCopy() *BottlerocketKernelSettings { -+ if in == nil { -+ return nil -+ } -+ out := new(BottlerocketKernelSettings) -+ in.DeepCopyInto(out) -+ return out -+} -+ - // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. - func (in *BottlerocketKubernetesSettings) DeepCopyInto(out *BottlerocketKubernetesSettings) { - *out = *in -@@ -255,6 +277,11 @@ func (in *BottlerocketSettings) DeepCopyInto(out *BottlerocketSettings) { - *out = new(BottlerocketKubernetesSettings) - (*in).DeepCopyInto(*out) - } -+ if in.Kernel != nil { -+ in, out := &in.Kernel, &out.Kernel -+ *out = new(BottlerocketKernelSettings) -+ (*in).DeepCopyInto(*out) -+ } - } - - // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketSettings. -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -index 6c0a1ff00..605e3b55d 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -@@ -1241,6 +1241,17 @@ spec: - description: Bottlerocket holds configuration for certain bottlerocket - settings. This is only for bottlerocket. - properties: -+ kernel: -+ description: KernelSettings contains additional kernel settings -+ for Bottlerocket. -+ properties: -+ sysctlSettings: -+ additionalProperties: -+ type: string -+ description: SysctlSettings defines the kernel sysctl -+ settings to set for bottlerocket nodes. -+ type: object -+ type: object - kubernetes: - description: Kubernetes holds the kubernetes settings for - bottlerocket nodes. -@@ -2059,6 +2070,17 @@ spec: - description: Bottlerocket holds configuration for certain bottlerocket - settings. This is only for bottlerocket. - properties: -+ kernel: -+ description: KernelSettings contains additional kernel settings -+ for Bottlerocket. -+ properties: -+ sysctlSettings: -+ additionalProperties: -+ type: string -+ description: SysctlSettings defines the kernel sysctl -+ settings to set for bottlerocket nodes. -+ type: object -+ type: object - kubernetes: - description: Kubernetes holds the kubernetes settings for - bottlerocket nodes. -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -index 1bf94de01..5227b7333 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -@@ -1274,6 +1274,17 @@ spec: - description: Bottlerocket holds configuration for certain - bottlerocket settings. This is only for bottlerocket. - properties: -+ kernel: -+ description: KernelSettings contains additional kernel -+ settings for Bottlerocket. -+ properties: -+ sysctlSettings: -+ additionalProperties: -+ type: string -+ description: SysctlSettings defines the kernel -+ sysctl settings to set for bottlerocket nodes. -+ type: object -+ type: object - kubernetes: - description: Kubernetes holds the kubernetes settings - for bottlerocket nodes. -@@ -2149,6 +2160,17 @@ spec: - description: Bottlerocket holds configuration for certain - bottlerocket settings. This is only for bottlerocket. - properties: -+ kernel: -+ description: KernelSettings contains additional kernel -+ settings for Bottlerocket. -+ properties: -+ sysctlSettings: -+ additionalProperties: -+ type: string -+ description: SysctlSettings defines the kernel -+ sysctl settings to set for bottlerocket nodes. -+ type: object -+ type: object - kubernetes: - description: Kubernetes holds the kubernetes settings - for bottlerocket nodes. -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -index e5926de86..a23a43668 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -@@ -113,6 +113,12 @@ password = "{{.RegistryMirrorPassword}}" - [settings.ntp] - time-servers = [{{stringsJoin .NTPServers ", " }}] - {{- end -}} -+` -+ -+ sysctlSettingsTemplate = `{{ define "sysctlSettingsTemplate" -}} -+[settings.kernel.sysctl] -+{{.SysctlSettings}} -+{{- end -}} - ` - - bottlerocketNodeInitSettingsTemplate = `{{template "hostContainerSlice" .}} -@@ -149,5 +155,9 @@ time-servers = [{{stringsJoin .NTPServers ", " }}] - {{- if .NTPServers}} - {{template "ntpSettings" .}} - {{- end -}} -+ -+{{- if (ne .SysctlSettings "")}} -+{{template "sysctlSettingsTemplate" .}} -+{{- end -}} - ` - ) -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -index 3463a2769..fdc60204d 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -@@ -253,6 +253,33 @@ essential = false - mode = "MODE" - source = "BOOTSTRAP_REPO:BOOTSTRAP_TAG" - user-data = "BOOTSTRAP_B6_4USERDATA"` -+ -+ kernelSettingsUserData = ` -+[settings.host-containers.admin] -+enabled = true -+superpowered = true -+source = "ADMIN_REPO:ADMIN_TAG" -+user-data = "CnsKCSJzc2giOiB7CgkJImF1dGhvcml6ZWQta2V5cyI6IFsic3NoLXJzYSBBQUEuLi4iXQoJfQp9" -+[settings.host-containers.kubeadm-bootstrap] -+enabled = true -+superpowered = true -+source = "BOOTSTRAP_REPO:BOOTSTRAP_TAG" -+user-data = "Qk9UVExFUk9DS0VUX0JPT1RTVFJBUF9VU0VSREFUQQ==" -+ -+[settings.kubernetes] -+cluster-domain = "cluster.local" -+standalone-mode = true -+authentication-mode = "tls" -+server-tls-bootstrap = false -+pod-infra-container-image = "PAUSE_REPO:PAUSE_TAG" -+provider-id = "PROVIDERID" -+ -+[settings.network] -+hostname = "hostname" -+[settings.kernel.sysctl] -+"foo" = "bar" -+"abc" = "def" -+` - ) - - var ( -@@ -465,6 +492,27 @@ func TestGetBottlerocketNodeUserData(t *testing.T) { - }, - output: customBootstrapUserData, - }, -+ { -+ name: "with kernel settings", -+ config: &BottlerocketConfig{ -+ BottlerocketAdmin: brAdmin, -+ BottlerocketBootstrap: brBootstrap, -+ Hostname: hostname, -+ Pause: pause, -+ KubeletExtraArgs: map[string]string{ -+ "provider-id": "PROVIDERID", -+ }, -+ BottlerocketSettings: &bootstrapv1.BottlerocketSettings{ -+ Kernel: &bootstrapv1.BottlerocketKernelSettings{ -+ SysctlSettings: map[string]string{ -+ "foo": "bar", -+ "abc": "def", -+ }, -+ }, -+ }, -+ }, -+ output: kernelSettingsUserData, -+ }, - } - for _, testcase := range testcases { - t.Run(testcase.name, func(t *testing.T) { -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -index cbab7c7a4..afd854f1c 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -@@ -55,10 +55,11 @@ type BottlerocketSettingsInput struct { - ProviderID string - Hostname string - AllowedUnsafeSysctls []string -- ClusterDNSIPs []string -+ ClusterDNSIPs []string - MaxPods int - HostContainers []bootstrapv1.BottlerocketHostContainer - BootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer -+ SysctlSettings string - } - - // HostPath holds the path and type of a host path volume. -@@ -156,6 +157,9 @@ func generateNodeUserData(kind string, tpl string, data interface{}) ([]byte, er - if _, err := tm.Parse(ntpTemplate); err != nil { - return nil, errors.Wrapf(err, "failed to parse NTP %s template", kind) - } -+ if _, err := tm.Parse(sysctlSettingsTemplate); err != nil { -+ return nil, errors.Wrapf(err, "failed to parse sysctl settings %s template", kind) -+ } - t, err := tm.Parse(tpl) - if err != nil { - return nil, errors.Wrapf(err, "failed to parse %s template", kind) -@@ -239,14 +243,20 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot - bottlerocketInput.NTPServers = append(bottlerocketInput.NTPServers, strconv.Quote(ntp)) - } - } -- if config.BottlerocketSettings != nil && config.BottlerocketSettings.Kubernetes != nil { -- bottlerocketInput.MaxPods = config.BottlerocketSettings.Kubernetes.MaxPods -- for _, sysctl := range config.BottlerocketSettings.Kubernetes.AllowedUnsafeSysctls { -- bottlerocketInput.AllowedUnsafeSysctls = append(bottlerocketInput.AllowedUnsafeSysctls, strconv.Quote(sysctl)) -+ if config.BottlerocketSettings != nil { -+ if config.BottlerocketSettings.Kubernetes != nil { -+ bottlerocketInput.MaxPods = config.BottlerocketSettings.Kubernetes.MaxPods -+ for _, sysctl := range config.BottlerocketSettings.Kubernetes.AllowedUnsafeSysctls { -+ bottlerocketInput.AllowedUnsafeSysctls = append(bottlerocketInput.AllowedUnsafeSysctls, strconv.Quote(sysctl)) -+ } -+ for _, ip := range config.BottlerocketSettings.Kubernetes.ClusterDNSIPs { -+ bottlerocketInput.ClusterDNSIPs = append(bottlerocketInput.ClusterDNSIPs, strconv.Quote(ip)) -+ } - } -- for _, ip := range config.BottlerocketSettings.Kubernetes.ClusterDNSIPs { -- bottlerocketInput.ClusterDNSIPs = append(bottlerocketInput.ClusterDNSIPs, strconv.Quote(ip)) -+ if config.BottlerocketSettings.Kernel != nil { -+ bottlerocketInput.SysctlSettings = parseSysctlSettings(config.BottlerocketSettings.Kernel.SysctlSettings) - } -+ - } - - return generateNodeUserData("InitBottlerocketNode", bottlerocketNodeInitSettingsTemplate, bottlerocketInput) -@@ -297,6 +307,14 @@ func parseNodeLabels(nodeLabels string) string { - return nodeLabelsToml - } - -+func parseSysctlSettings(sysctlSettings map[string]string) string { -+ sysctlSettingsToml := "" -+ for key, value := range sysctlSettings { -+ sysctlSettingsToml += fmt.Sprintf("\"%v\" = \"%v\"\n", key, value) -+ } -+ return sysctlSettingsToml -+} -+ - // Parses through all the users and return list of all user's authorized ssh keys - func getAllAuthorizedKeys(users []bootstrapv1.User) string { - var sshAuthorizedKeys []string -diff --git a/controlplane/kubeadm/api/v1alpha4/zz_generated.deepcopy.go b/controlplane/kubeadm/api/v1alpha4/zz_generated.deepcopy.go -index df2807f5d..4ad231410 100644 ---- a/controlplane/kubeadm/api/v1alpha4/zz_generated.deepcopy.go -+++ b/controlplane/kubeadm/api/v1alpha4/zz_generated.deepcopy.go -@@ -22,7 +22,7 @@ package v1alpha4 - - import ( - "k8s.io/apimachinery/pkg/apis/meta/v1" -- runtime "k8s.io/apimachinery/pkg/runtime" -+ "k8s.io/apimachinery/pkg/runtime" - "k8s.io/apimachinery/pkg/util/intstr" - apiv1alpha4 "sigs.k8s.io/cluster-api/api/v1alpha4" - ) -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -index 5ed727e20..f811f9a25 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -@@ -1519,6 +1519,17 @@ spec: - description: Bottlerocket holds configuration for certain - bottlerocket settings. This is only for bottlerocket. - properties: -+ kernel: -+ description: KernelSettings contains additional kernel -+ settings for Bottlerocket. -+ properties: -+ sysctlSettings: -+ additionalProperties: -+ type: string -+ description: SysctlSettings defines the kernel sysctl -+ settings to set for bottlerocket nodes. -+ type: object -+ type: object - kubernetes: - description: Kubernetes holds the kubernetes settings - for bottlerocket nodes. -@@ -2372,6 +2383,17 @@ spec: - description: Bottlerocket holds configuration for certain - bottlerocket settings. This is only for bottlerocket. - properties: -+ kernel: -+ description: KernelSettings contains additional kernel -+ settings for Bottlerocket. -+ properties: -+ sysctlSettings: -+ additionalProperties: -+ type: string -+ description: SysctlSettings defines the kernel sysctl -+ settings to set for bottlerocket nodes. -+ type: object -+ type: object - kubernetes: - description: Kubernetes holds the kubernetes settings - for bottlerocket nodes. -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -index 90ddceaaf..61a9c61db 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -@@ -1473,6 +1473,18 @@ spec: - certain bottlerocket settings. This is only for - bottlerocket. - properties: -+ kernel: -+ description: KernelSettings contains additional -+ kernel settings for Bottlerocket. -+ properties: -+ sysctlSettings: -+ additionalProperties: -+ type: string -+ description: SysctlSettings defines the kernel -+ sysctl settings to set for bottlerocket -+ nodes. -+ type: object -+ type: object - kubernetes: - description: Kubernetes holds the kubernetes settings - for bottlerocket nodes. -@@ -2385,6 +2397,18 @@ spec: - certain bottlerocket settings. This is only for - bottlerocket. - properties: -+ kernel: -+ description: KernelSettings contains additional -+ kernel settings for Bottlerocket. -+ properties: -+ sysctlSettings: -+ additionalProperties: -+ type: string -+ description: SysctlSettings defines the kernel -+ sysctl settings to set for bottlerocket -+ nodes. -+ type: object -+ type: object - kubernetes: - description: Kubernetes holds the kubernetes settings - for bottlerocket nodes. --- -2.39.3 (Apple Git-145) - diff --git a/projects/kubernetes-sigs/cluster-api/patches/0029-Add-support-for-custom-cert-bundles-in-BR-21.patch b/projects/kubernetes-sigs/cluster-api/patches/0029-Add-support-for-custom-cert-bundles-in-BR-21.patch new file mode 100644 index 0000000000..df7984aeef --- /dev/null +++ b/projects/kubernetes-sigs/cluster-api/patches/0029-Add-support-for-custom-cert-bundles-in-BR-21.patch @@ -0,0 +1,1230 @@ +From 3a2f54810f88c77f125a1d4226f7f928123e0fe1 Mon Sep 17 00:00:00 2001 +From: ahreehong <46465244+ahreehong@users.noreply.github.com> +Date: Fri, 19 May 2023 16:29:08 -0400 +Subject: [PATCH 29/40] Add support for custom cert bundles in BR (#21) + +* add support for custom cert bundles br + +* take in non base-64 encoded data for cert + +Signed-off-by: Ahree Hong +--- + .../kubeadm/api/v1alpha4/kubeadm_types.go | 17 +++ + .../api/v1alpha4/zz_generated.conversion.go | 36 +++++++ + .../api/v1alpha4/zz_generated.deepcopy.go | 25 +++++ + .../kubeadm/api/v1beta1/kubeadm_types.go | 17 +++ + .../api/v1beta1/zz_generated.deepcopy.go | 25 +++++ + ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 96 +++++++++++++++++ + ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 102 ++++++++++++++++++ + .../internal/bottlerocket/bootstrap.go | 16 +++ + .../internal/bottlerocket/bootstrap_test.go | 53 +++++++++ + .../internal/bottlerocket/bottlerocket.go | 14 +++ + .../controllers/kubeadmconfig_controller.go | 9 ++ + .../kubeadm/types/upstreamv1beta1/types.go | 17 +++ + .../zz_generated.conversion.go | 36 +++++++ + .../upstreamv1beta1/zz_generated.deepcopy.go | 25 +++++ + .../zz_generated.conversion.go | 2 + + .../zz_generated.conversion.go | 2 + + ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 96 +++++++++++++++++ + ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 68 ++++++++++++ + 18 files changed, 656 insertions(+) + +diff --git a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +index 010efa948..3d43cae72 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +@@ -171,6 +171,10 @@ type ClusterConfiguration struct { + // This is only for bottlerocket. + // +optional + Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` ++ ++ // CertBundles holds additional trusted cert bundles. ++ // +optional ++ CertBundles []CertBundle `json:"certBundles,omitempty"` + } + + // BottlerocketSettings define bottlerocket settings that can be configured on bottlerocket nodes. +@@ -534,6 +538,10 @@ type JoinConfiguration struct { + // This is only for bottlerocket. + // +optional + Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` ++ ++ // CertBundles holds additional trusted cert bundles. ++ // +optional ++ CertBundles []CertBundle `json:"certBundles,omitempty"` + } + + // BottlerocketHostContainer describes a host image for Bottlerocket +@@ -574,6 +582,15 @@ type BottlerocketBootstrapContainer struct { + UserData string `json:"userData,omitempty"` + } + ++// CertBundle holds the cert data. ++type CertBundle struct { ++ // Name is the name of the cert bundle. ++ Name string `json:"name"` ++ ++ // Data is the actual cert. ++ Data string `json:"data"` ++} ++ + // JoinControlPlane contains elements describing an additional control plane instance to be deployed on the joining node. + type JoinControlPlane struct { + // LocalAPIEndpoint represents the endpoint of the API server instance to be deployed on this node. +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +index 8f36b6a13..c02aee696 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +@@ -180,6 +180,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*CertBundle)(nil), (*v1beta1.CertBundle)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_CertBundle_To_v1beta1_CertBundle(a.(*CertBundle), b.(*v1beta1.CertBundle), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.CertBundle)(nil), (*CertBundle)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_CertBundle_To_v1alpha4_CertBundle(a.(*v1beta1.CertBundle), b.(*CertBundle), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*ClusterConfiguration)(nil), (*v1beta1.ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(a.(*ClusterConfiguration), b.(*v1beta1.ClusterConfiguration), scope) + }); err != nil { +@@ -883,6 +893,28 @@ func Convert_v1beta1_BottlerocketSettings_To_v1alpha4_BottlerocketSettings(in *v + return autoConvert_v1beta1_BottlerocketSettings_To_v1alpha4_BottlerocketSettings(in, out, s) + } + ++func autoConvert_v1alpha4_CertBundle_To_v1beta1_CertBundle(in *CertBundle, out *v1beta1.CertBundle, s conversion.Scope) error { ++ out.Name = in.Name ++ out.Data = in.Data ++ return nil ++} ++ ++// Convert_v1alpha4_CertBundle_To_v1beta1_CertBundle is an autogenerated conversion function. ++func Convert_v1alpha4_CertBundle_To_v1beta1_CertBundle(in *CertBundle, out *v1beta1.CertBundle, s conversion.Scope) error { ++ return autoConvert_v1alpha4_CertBundle_To_v1beta1_CertBundle(in, out, s) ++} ++ ++func autoConvert_v1beta1_CertBundle_To_v1alpha4_CertBundle(in *v1beta1.CertBundle, out *CertBundle, s conversion.Scope) error { ++ out.Name = in.Name ++ out.Data = in.Data ++ return nil ++} ++ ++// Convert_v1beta1_CertBundle_To_v1alpha4_CertBundle is an autogenerated conversion function. ++func Convert_v1beta1_CertBundle_To_v1alpha4_CertBundle(in *v1beta1.CertBundle, out *CertBundle, s conversion.Scope) error { ++ return autoConvert_v1beta1_CertBundle_To_v1alpha4_CertBundle(in, out, s) ++} ++ + func autoConvert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *ClusterConfiguration, out *v1beta1.ClusterConfiguration, s conversion.Scope) error { + if err := Convert_v1alpha4_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { + return err +@@ -929,6 +961,7 @@ func autoConvert_v1alpha4_ClusterConfiguration_To_v1beta1_ClusterConfiguration(i + out.BottlerocketHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]v1beta1.BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + out.Bottlerocket = (*v1beta1.BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) ++ out.CertBundles = *(*[]v1beta1.CertBundle)(unsafe.Pointer(&in.CertBundles)) + return nil + } + +@@ -983,6 +1016,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(i + out.BottlerocketHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + out.Bottlerocket = (*BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) ++ out.CertBundles = *(*[]CertBundle)(unsafe.Pointer(&in.CertBundles)) + return nil + } + +@@ -1359,6 +1393,7 @@ func autoConvert_v1alpha4_JoinConfiguration_To_v1beta1_JoinConfiguration(in *Joi + out.BottlerocketCustomHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]v1beta1.BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + out.Bottlerocket = (*v1beta1.BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) ++ out.CertBundles = *(*[]v1beta1.CertBundle)(unsafe.Pointer(&in.CertBundles)) + return nil + } + +@@ -1399,6 +1434,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1b + out.BottlerocketCustomHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + out.Bottlerocket = (*BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) ++ out.CertBundles = *(*[]CertBundle)(unsafe.Pointer(&in.CertBundles)) + return nil + } + +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +index f8d8004c0..4c3225e59 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +@@ -330,6 +330,21 @@ func (in *BottlerocketSettings) DeepCopy() *BottlerocketSettings { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *CertBundle) DeepCopyInto(out *CertBundle) { ++ *out = *in ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CertBundle. ++func (in *CertBundle) DeepCopy() *CertBundle { ++ if in == nil { ++ return nil ++ } ++ out := new(CertBundle) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = *in +@@ -368,6 +383,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = new(BottlerocketSettings) + (*in).DeepCopyInto(*out) + } ++ if in.CertBundles != nil { ++ in, out := &in.CertBundles, &out.CertBundles ++ *out = make([]CertBundle, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. +@@ -747,6 +767,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = new(BottlerocketSettings) + (*in).DeepCopyInto(*out) + } ++ if in.CertBundles != nil { ++ in, out := &in.CertBundles, &out.CertBundles ++ *out = make([]CertBundle, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. +diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +index 434d2c088..ed965709a 100644 +--- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +@@ -190,6 +190,10 @@ type ClusterConfiguration struct { + // This is only for bottlerocket. + // +optional + Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` ++ ++ // CertBundles holds additional trusted cert bundles. ++ // +optional ++ CertBundles []CertBundle `json:"certBundles,omitempty"` + } + + // BottlerocketSettings define bottlerocket settings that can be configured on bottlerocket nodes. +@@ -621,6 +625,10 @@ type JoinConfiguration struct { + // This is only for bottlerocket. + // +optional + Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` ++ ++ // CertBundles holds additional trusted cert bundles. ++ // +optional ++ CertBundles []CertBundle `json:"certBundles,omitempty"` + } + + // BottlerocketHostContainer describes a host image for Bottlerocket +@@ -661,6 +669,15 @@ type BottlerocketBootstrapContainer struct { + UserData string `json:"userData,omitempty"` + } + ++// CertBundle holds the cert data. ++type CertBundle struct { ++ // Name is the name of the cert bundle. ++ Name string `json:"name"` ++ ++ // Data is the actual cert. ++ Data string `json:"data"` ++} ++ + // JoinControlPlane contains elements describing an additional control plane instance to be deployed on the joining node. + type JoinControlPlane struct { + // LocalAPIEndpoint represents the endpoint of the API server instance to be deployed on this node. +diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +index c89d4aa1f..9fefdcb62 100644 +--- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +@@ -330,6 +330,21 @@ func (in *BottlerocketSettings) DeepCopy() *BottlerocketSettings { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *CertBundle) DeepCopyInto(out *CertBundle) { ++ *out = *in ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CertBundle. ++func (in *CertBundle) DeepCopy() *CertBundle { ++ if in == nil { ++ return nil ++ } ++ out := new(CertBundle) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = *in +@@ -368,6 +383,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = new(BottlerocketSettings) + (*in).DeepCopyInto(*out) + } ++ if in.CertBundles != nil { ++ in, out := &in.CertBundles, &out.CertBundles ++ *out = make([]CertBundle, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. +@@ -802,6 +822,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = new(BottlerocketSettings) + (*in).DeepCopyInto(*out) + } ++ if in.CertBundles != nil { ++ in, out := &in.CertBundles, &out.CertBundles ++ *out = make([]CertBundle, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +index 0591279db..3b4cbbf3f 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +@@ -280,6 +280,22 @@ spec: + - superpowered + type: object + type: array ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store or look + for all required certificates. NB: if not provided, this will +@@ -1061,6 +1077,22 @@ spec: + Defaults to "/etc/kubernetes/pki/ca.crt". TODO: revisit when + there is defaulting from k/k' + type: string ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + controlPlane: + description: ControlPlane defines the additional control plane + instance to be deployed on the joining node. If nil, no additional +@@ -1709,6 +1741,22 @@ spec: + - superpowered + type: object + type: array ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store or look + for all required certificates. NB: if not provided, this will +@@ -2486,6 +2534,22 @@ spec: + Defaults to "/etc/kubernetes/pki/ca.crt". TODO: revisit when + there is defaulting from k/k' + type: string ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + controlPlane: + description: ControlPlane defines the additional control plane + instance to be deployed on the joining node. If nil, no additional +@@ -3132,6 +3196,22 @@ spec: + - superpowered + type: object + type: array ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store or look + for all required certificates. NB: if not provided, this will +@@ -3978,6 +4058,22 @@ spec: + Defaults to "/etc/kubernetes/pki/ca.crt". TODO: revisit when + there is defaulting from k/k' + type: string ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + controlPlane: + description: ControlPlane defines the additional control plane + instance to be deployed on the joining node. If nil, no additional +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +index 75574d5e7..e25795947 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +@@ -298,6 +298,23 @@ spec: + - superpowered + type: object + type: array ++ certBundles: ++ description: CertBundles holds additional trusted cert ++ bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store + or look for all required certificates. NB: if not provided, +@@ -1126,6 +1143,23 @@ spec: + and control-plane. Defaults to "/etc/kubernetes/pki/ca.crt". + TODO: revisit when there is defaulting from k/k' + type: string ++ certBundles: ++ description: CertBundles holds additional trusted cert ++ bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + controlPlane: + description: ControlPlane defines the additional control + plane instance to be deployed on the joining node. If +@@ -1741,6 +1775,23 @@ spec: + - superpowered + type: object + type: array ++ certBundles: ++ description: CertBundles holds additional trusted cert ++ bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store + or look for all required certificates. NB: if not provided, +@@ -2567,6 +2618,23 @@ spec: + and control-plane. Defaults to "/etc/kubernetes/pki/ca.crt". + TODO: revisit when there is defaulting from k/k' + type: string ++ certBundles: ++ description: CertBundles holds additional trusted cert ++ bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + controlPlane: + description: ControlPlane defines the additional control + plane instance to be deployed on the joining node. If +@@ -3205,6 +3273,23 @@ spec: + - superpowered + type: object + type: array ++ certBundles: ++ description: CertBundles holds additional trusted cert ++ bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store + or look for all required certificates. NB: if not provided, +@@ -4108,6 +4193,23 @@ spec: + and control-plane. Defaults to "/etc/kubernetes/pki/ca.crt". + TODO: revisit when there is defaulting from k/k' + type: string ++ certBundles: ++ description: CertBundles holds additional trusted cert ++ bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + controlPlane: + description: ControlPlane defines the additional control + plane instance to be deployed on the joining node. If +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +index 901db1cb7..df222b943 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +@@ -128,6 +128,18 @@ reboot-to-reconcile = true + [settings.boot.kernel-parameters] + {{.BootKernel}} + {{- end -}} ++` ++ certsTemplate = `{{ define "certsSettings" -}} ++[settings.pki.{{.Name}}] ++data = "{{.Data}}" ++trusted = true ++{{- end -}} ++` ++ certBundlesSliceTemplate = `{{ define "certBundlesSlice" -}} ++{{- range $cBundle := .CertBundles }} ++{{template "certsSettings" $cBundle }} ++{{- end -}} ++{{- end -}} + ` + + bottlerocketNodeInitSettingsTemplate = `{{template "hostContainerSlice" .}} +@@ -172,5 +184,9 @@ reboot-to-reconcile = true + {{- if .BootKernel}} + {{template "bootSettings" .}} + {{- end -}} ++ ++{{- if .CertBundles}} ++{{template "certBundlesSlice" .}} ++{{- end -}} + ` + ) +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +index 5846524be..2ee2d942b 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +@@ -310,6 +310,36 @@ reboot-to-reconcile = true + "abc" = ["def","123"] + "foo" = ["bar"] + ` ++ ++ userDataWithCertBundle = ` ++[settings.host-containers.admin] ++enabled = true ++superpowered = true ++source = "ADMIN_REPO:ADMIN_TAG" ++user-data = "CnsKCSJzc2giOiB7CgkJImF1dGhvcml6ZWQta2V5cyI6IFsic3NoLXJzYSBBQUEuLi4iXQoJfQp9" ++[settings.host-containers.kubeadm-bootstrap] ++enabled = true ++superpowered = true ++source = "BOOTSTRAP_REPO:BOOTSTRAP_TAG" ++user-data = "Qk9UVExFUk9DS0VUX0JPT1RTVFJBUF9VU0VSREFUQQ==" ++ ++[settings.kubernetes] ++cluster-domain = "cluster.local" ++standalone-mode = true ++authentication-mode = "tls" ++server-tls-bootstrap = false ++pod-infra-container-image = "PAUSE_REPO:PAUSE_TAG" ++provider-id = "PROVIDERID" ++ ++[settings.network] ++hostname = "hostname" ++ ++[settings.pki.bundle1] ++data = "QUJDREVG" ++trusted = true ++[settings.pki.bundle2] ++data = "MTIzNDU2" ++trusted = true` + ) + + var ( +@@ -569,6 +599,29 @@ func TestGetBottlerocketNodeUserData(t *testing.T) { + }, + output: BootSettingsUserData, + }, ++ { ++ name: "with custom cert bundle settings", ++ config: &BottlerocketConfig{ ++ BottlerocketAdmin: brAdmin, ++ BottlerocketBootstrap: brBootstrap, ++ Hostname: hostname, ++ Pause: pause, ++ KubeletExtraArgs: map[string]string{ ++ "provider-id": "PROVIDERID", ++ }, ++ CertBundle: []bootstrapv1.CertBundle{ ++ { ++ Name: "bundle1", ++ Data: "ABCDEF", ++ }, ++ { ++ Name: "bundle2", ++ Data: "123456", ++ }, ++ }, ++ }, ++ output: userDataWithCertBundle, ++ }, + } + for _, testcase := range testcases { + t.Run(testcase.name, func(t *testing.T) { +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +index 7b7131829..ce796f206 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +@@ -37,6 +37,7 @@ type BottlerocketConfig struct { + BottlerocketCustomBootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer + NTPServers []string + Hostname string ++ CertBundle []bootstrapv1.CertBundle + RegistryMirrorCredentials + } + +@@ -61,6 +62,7 @@ type BottlerocketSettingsInput struct { + HostContainers []bootstrapv1.BottlerocketHostContainer + BootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer + SysctlSettings string ++ CertBundles []bootstrapv1.CertBundle + } + + // HostPath holds the path and type of a host path volume. +@@ -164,6 +166,12 @@ func generateNodeUserData(kind string, tpl string, data interface{}) ([]byte, er + if _, err := tm.Parse(bootSettingsTemplate); err != nil { + return nil, errors.Wrapf(err, "failed to parse boot settings %s template", kind) + } ++ if _, err := tm.Parse(certsTemplate); err != nil { ++ return nil, errors.Wrapf(err, "failed to parse certs %s template", kind) ++ } ++ if _, err := tm.Parse(certBundlesSliceTemplate); err != nil { ++ return nil, errors.Wrapf(err, "failed to parse cert bundles %s template", kind) ++ } + t, err := tm.Parse(tpl) + if err != nil { + return nil, errors.Wrapf(err, "failed to parse %s template", kind) +@@ -266,6 +274,12 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot + } + + } ++ if config.CertBundle != nil { ++ for _, cert := range config.CertBundle { ++ cert.Data = base64.StdEncoding.EncodeToString([]byte(cert.Data)) ++ bottlerocketInput.CertBundles = append(bottlerocketInput.CertBundles, cert) ++ } ++ } + + return generateNodeUserData("InitBottlerocketNode", bottlerocketNodeInitSettingsTemplate, bottlerocketInput) + } +diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go +index b63a64589..4e8b7c5e0 100644 +--- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go ++++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go +@@ -509,6 +509,9 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex + if scope.Config.Spec.NTP != nil && scope.Config.Spec.NTP.Enabled != nil && *scope.Config.Spec.NTP.Enabled { + bottlerocketConfig.NTPServers = scope.Config.Spec.NTP.Servers + } ++ if scope.Config.Spec.ClusterConfiguration.CertBundles != nil { ++ bottlerocketConfig.CertBundle = scope.Config.Spec.ClusterConfiguration.CertBundles ++ } + } + + clusterdata, err := kubeadmtypes.MarshalClusterConfigurationForVersion(scope.Config.Spec.ClusterConfiguration, parsedVersion) +@@ -734,6 +737,9 @@ func (r *KubeadmConfigReconciler) joinWorker(ctx context.Context, scope *Scope) + if scope.Config.Spec.NTP != nil && scope.Config.Spec.NTP.Enabled != nil && *scope.Config.Spec.NTP.Enabled { + bottlerocketConfig.NTPServers = scope.Config.Spec.NTP.Servers + } ++ if scope.Config.Spec.JoinConfiguration.CertBundles != nil { ++ bottlerocketConfig.CertBundle = scope.Config.Spec.JoinConfiguration.CertBundles ++ } + bootstrapJoinData, err = bottlerocket.NewNode(nodeInput, bottlerocketConfig) + if err != nil { + scope.Error(err, "Failed to create a worker bottlerocket join configuration") +@@ -881,6 +887,9 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S + if scope.Config.Spec.NTP != nil && scope.Config.Spec.NTP.Enabled != nil && *scope.Config.Spec.NTP.Enabled { + bottlerocketConfig.NTPServers = scope.Config.Spec.NTP.Servers + } ++ if scope.Config.Spec.JoinConfiguration.CertBundles != nil { ++ bottlerocketConfig.CertBundle = scope.Config.Spec.JoinConfiguration.CertBundles ++ } + bootstrapJoinData, err = bottlerocket.NewJoinControlPlane(controlPlaneJoinInput, bottlerocketConfig) + if err != nil { + scope.Error(err, "Failed to generate cloud init for bottlerocket bootstrap control plane") +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/types.go b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +index 1b7ce57fe..be0b0725c 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/types.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +@@ -169,6 +169,10 @@ type ClusterConfiguration struct { + // This is only for bottlerocket. + // +optional + Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` ++ ++ // CertBundles holds additional trusted cert bundles. ++ // +optional ++ CertBundles []CertBundle `json:"certBundles,omitempty"` + } + + // BottlerocketSettings define bottlerocket settings that can be configured on bottlerocket nodes. +@@ -523,6 +527,10 @@ type JoinConfiguration struct { + // This is only for bottlerocket. + // +optional + Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` ++ ++ // CertBundles holds additional trusted cert bundles. ++ // +optional ++ CertBundles []CertBundle `json:"certBundles,omitempty"` + } + + // BottlerocketHostContainer describes a host image for Bottlerocket +@@ -563,6 +571,15 @@ type BottlerocketBootstrapContainer struct { + UserData string `json:"userData,omitempty"` + } + ++// CertBundle holds the cert data. ++type CertBundle struct { ++ // Name is the name of the cert bundle. ++ Name string `json:"name"` ++ ++ // Data is the actual cert. ++ Data string `json:"data"` ++} ++ + // JoinControlPlane contains elements describing an additional control plane instance to be deployed on the joining node. + type JoinControlPlane struct { + // LocalAPIEndpoint represents the endpoint of the API server instance to be deployed on this node. +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go +index 5cef55e28..f77e22f31 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go +@@ -178,6 +178,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*CertBundle)(nil), (*v1beta1.CertBundle)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_CertBundle_To_v1beta1_CertBundle(a.(*CertBundle), b.(*v1beta1.CertBundle), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.CertBundle)(nil), (*CertBundle)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_CertBundle_To_upstreamv1beta1_CertBundle(a.(*v1beta1.CertBundle), b.(*CertBundle), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*v1beta1.ClusterConfiguration)(nil), (*ClusterConfiguration)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_ClusterConfiguration_To_upstreamv1beta1_ClusterConfiguration(a.(*v1beta1.ClusterConfiguration), b.(*ClusterConfiguration), scope) + }); err != nil { +@@ -721,6 +731,28 @@ func Convert_v1beta1_BottlerocketSettings_To_upstreamv1beta1_BottlerocketSetting + return autoConvert_v1beta1_BottlerocketSettings_To_upstreamv1beta1_BottlerocketSettings(in, out, s) + } + ++func autoConvert_upstreamv1beta1_CertBundle_To_v1beta1_CertBundle(in *CertBundle, out *v1beta1.CertBundle, s conversion.Scope) error { ++ out.Name = in.Name ++ out.Data = in.Data ++ return nil ++} ++ ++// Convert_upstreamv1beta1_CertBundle_To_v1beta1_CertBundle is an autogenerated conversion function. ++func Convert_upstreamv1beta1_CertBundle_To_v1beta1_CertBundle(in *CertBundle, out *v1beta1.CertBundle, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_CertBundle_To_v1beta1_CertBundle(in, out, s) ++} ++ ++func autoConvert_v1beta1_CertBundle_To_upstreamv1beta1_CertBundle(in *v1beta1.CertBundle, out *CertBundle, s conversion.Scope) error { ++ out.Name = in.Name ++ out.Data = in.Data ++ return nil ++} ++ ++// Convert_v1beta1_CertBundle_To_upstreamv1beta1_CertBundle is an autogenerated conversion function. ++func Convert_v1beta1_CertBundle_To_upstreamv1beta1_CertBundle(in *v1beta1.CertBundle, out *CertBundle, s conversion.Scope) error { ++ return autoConvert_v1beta1_CertBundle_To_upstreamv1beta1_CertBundle(in, out, s) ++} ++ + func autoConvert_upstreamv1beta1_ClusterConfiguration_To_v1beta1_ClusterConfiguration(in *ClusterConfiguration, out *v1beta1.ClusterConfiguration, s conversion.Scope) error { + if err := Convert_upstreamv1beta1_Pause_To_v1beta1_Pause(&in.Pause, &out.Pause, s); err != nil { + return err +@@ -768,6 +800,7 @@ func autoConvert_upstreamv1beta1_ClusterConfiguration_To_v1beta1_ClusterConfigur + out.BottlerocketHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]v1beta1.BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + out.Bottlerocket = (*v1beta1.BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) ++ out.CertBundles = *(*[]v1beta1.CertBundle)(unsafe.Pointer(&in.CertBundles)) + return nil + } + +@@ -817,6 +850,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta1_ClusterConfigur + out.BottlerocketHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + out.Bottlerocket = (*BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) ++ out.CertBundles = *(*[]CertBundle)(unsafe.Pointer(&in.CertBundles)) + return nil + } + +@@ -1090,6 +1124,7 @@ func autoConvert_upstreamv1beta1_JoinConfiguration_To_v1beta1_JoinConfiguration( + out.BottlerocketCustomHostContainers = *(*[]v1beta1.BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]v1beta1.BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + out.Bottlerocket = (*v1beta1.BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) ++ out.CertBundles = *(*[]v1beta1.CertBundle)(unsafe.Pointer(&in.CertBundles)) + return nil + } + +@@ -1130,6 +1165,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta1_JoinConfiguration( + out.BottlerocketCustomHostContainers = *(*[]BottlerocketHostContainer)(unsafe.Pointer(&in.BottlerocketCustomHostContainers)) + out.BottlerocketCustomBootstrapContainers = *(*[]BottlerocketBootstrapContainer)(unsafe.Pointer(&in.BottlerocketCustomBootstrapContainers)) + out.Bottlerocket = (*BottlerocketSettings)(unsafe.Pointer(in.Bottlerocket)) ++ out.CertBundles = *(*[]CertBundle)(unsafe.Pointer(&in.CertBundles)) + return nil + } + +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +index 2043410cf..ef10cb0b3 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +@@ -329,6 +329,21 @@ func (in *BottlerocketSettings) DeepCopy() *BottlerocketSettings { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *CertBundle) DeepCopyInto(out *CertBundle) { ++ *out = *in ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CertBundle. ++func (in *CertBundle) DeepCopy() *CertBundle { ++ if in == nil { ++ return nil ++ } ++ out := new(CertBundle) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = *in +@@ -367,6 +382,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + *out = new(BottlerocketSettings) + (*in).DeepCopyInto(*out) + } ++ if in.CertBundles != nil { ++ in, out := &in.CertBundles, &out.CertBundles ++ *out = make([]CertBundle, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. +@@ -646,6 +666,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + *out = new(BottlerocketSettings) + (*in).DeepCopyInto(*out) + } ++ if in.CertBundles != nil { ++ in, out := &in.CertBundles, &out.CertBundles ++ *out = make([]CertBundle, len(*in)) ++ copy(*out, *in) ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. +diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go +index 8b1acbb57..3b12557c4 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go +@@ -565,6 +565,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta2_ClusterConfigur + // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type + // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type + // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type ++ // WARNING: in.CertBundles requires manual conversion: does not exist in peer-type + return nil + } + +@@ -877,6 +878,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta2_JoinConfiguration( + // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type + // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type + // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type ++ // WARNING: in.CertBundles requires manual conversion: does not exist in peer-type + return nil + } + +diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go +index c613bdd12..6d812f516 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go +@@ -569,6 +569,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta3_ClusterConfigur + // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type + // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type + // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type ++ // WARNING: in.CertBundles requires manual conversion: does not exist in peer-type + return nil + } + +@@ -869,6 +870,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta3_JoinConfiguration( + // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type + // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type + // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type ++ // WARNING: in.CertBundles requires manual conversion: does not exist in peer-type + return nil + } + +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +index fc37c0601..fc1332eef 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +@@ -363,6 +363,22 @@ spec: + - superpowered + type: object + type: array ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store or + look for all required certificates. NB: if not provided, +@@ -1174,6 +1190,22 @@ spec: + control-plane. Defaults to "/etc/kubernetes/pki/ca.crt". + TODO: revisit when there is defaulting from k/k' + type: string ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + controlPlane: + description: ControlPlane defines the additional control plane + instance to be deployed on the joining node. If nil, no +@@ -1959,6 +1991,22 @@ spec: + - superpowered + type: object + type: array ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store or + look for all required certificates. NB: if not provided, +@@ -2767,6 +2815,22 @@ spec: + control-plane. Defaults to "/etc/kubernetes/pki/ca.crt". + TODO: revisit when there is defaulting from k/k' + type: string ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + controlPlane: + description: ControlPlane defines the additional control plane + instance to be deployed on the joining node. If nil, no +@@ -3636,6 +3700,22 @@ spec: + - superpowered + type: object + type: array ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store or + look for all required certificates. NB: if not provided, +@@ -4517,6 +4597,22 @@ spec: + control-plane. Defaults to "/etc/kubernetes/pki/ca.crt". + TODO: revisit when there is defaulting from k/k' + type: string ++ certBundles: ++ description: CertBundles holds additional trusted cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + controlPlane: + description: ControlPlane defines the additional control plane + instance to be deployed on the joining node. If nil, no +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +index c09d11044..ee4180f67 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +@@ -323,6 +323,23 @@ spec: + - superpowered + type: object + type: array ++ certBundles: ++ description: CertBundles holds additional trusted ++ cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store + or look for all required certificates. NB: if not +@@ -1185,6 +1202,23 @@ spec: + and control-plane. Defaults to "/etc/kubernetes/pki/ca.crt". + TODO: revisit when there is defaulting from k/k' + type: string ++ certBundles: ++ description: CertBundles holds additional trusted ++ cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + controlPlane: + description: ControlPlane defines the additional control + plane instance to be deployed on the joining node. +@@ -1992,6 +2026,23 @@ spec: + - superpowered + type: object + type: array ++ certBundles: ++ description: CertBundles holds additional trusted ++ cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + certificatesDir: + description: 'CertificatesDir specifies where to store + or look for all required certificates. NB: if not +@@ -2933,6 +2984,23 @@ spec: + and control-plane. Defaults to "/etc/kubernetes/pki/ca.crt". + TODO: revisit when there is defaulting from k/k' + type: string ++ certBundles: ++ description: CertBundles holds additional trusted ++ cert bundles. ++ items: ++ description: CertBundle holds the cert data. ++ properties: ++ data: ++ description: Data is the actual cert. ++ type: string ++ name: ++ description: Name is the name of the cert bundle. ++ type: string ++ required: ++ - data ++ - name ++ type: object ++ type: array + controlPlane: + description: ControlPlane defines the additional control + plane instance to be deployed on the joining node. +-- +2.42.0 + diff --git a/projects/kubernetes-sigs/cluster-api/patches/0029-add-boot-kernel-settings-for-BR.patch b/projects/kubernetes-sigs/cluster-api/patches/0029-add-boot-kernel-settings-for-BR.patch deleted file mode 100644 index f11f5fb6d8..0000000000 --- a/projects/kubernetes-sigs/cluster-api/patches/0029-add-boot-kernel-settings-for-BR.patch +++ /dev/null @@ -1,451 +0,0 @@ -From 944705bf50121b38cede2e12ba5f0e2a788fa07f Mon Sep 17 00:00:00 2001 -From: Ahree Hong -Date: Thu, 23 Mar 2023 01:51:16 -0700 -Subject: [PATCH 29/40] add boot kernel settings for BR - -Signed-off-by: Ahree Hong ---- - .../kubeadm/api/v1beta1/kubeadm_types.go | 8 +++ - .../api/v1beta1/zz_generated.deepcopy.go | 35 ++++++++++++ - ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 22 +++++++ - ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 22 +++++++ - .../internal/bottlerocket/bootstrap.go | 13 +++++ - .../internal/bottlerocket/bootstrap_test.go | 57 +++++++++++++++++++ - .../internal/bottlerocket/bottlerocket.go | 24 ++++++++ - ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 22 +++++++ - ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 22 +++++++ - .../machine/machine_controller_phases.go | 5 +- - 10 files changed, 228 insertions(+), 2 deletions(-) - -diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -index c97ef8604..434d2c088 100644 ---- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -+++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -@@ -201,6 +201,9 @@ type BottlerocketSettings struct { - // KernelSettings contains additional kernel settings for Bottlerocket. - // +optional - Kernel *BottlerocketKernelSettings `json:"kernel,omitempty"` -+ -+ // Boot holds the boot-related settings for bottlerocket nodes -+ Boot *BottlerocketBootSettings `json:"boot,omitempty"` - } - - // BottlerocketKubernetesSettings holds the settings for kubernetes on bottlerocket nodes. -@@ -222,6 +225,11 @@ type BottlerocketKernelSettings struct { - SysctlSettings map[string]string `json:"sysctlSettings,omitempty"` - } - -+// BottlerocketBootSettings holds the boot-related settings for bottlerocket nodes. -+type BottlerocketBootSettings struct { -+ BootKernelParameters map[string][]string `json:"bootKernelParameters,omitempty"` -+} -+ - // Pause defines the pause image repo and tag that should be run on the bootstrapped nodes. - // This setting is ONLY for bottlerocket nodes, as this needs to be set pre-boot time along with user-data - type Pause struct { -diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -index d335a35b1..09dcc431f 100644 ---- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -+++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -@@ -158,6 +158,36 @@ func (in *BottlerocketAdmin) DeepCopy() *BottlerocketAdmin { - return out - } - -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *BottlerocketBootSettings) DeepCopyInto(out *BottlerocketBootSettings) { -+ *out = *in -+ if in.BootKernelParameters != nil { -+ in, out := &in.BootKernelParameters, &out.BootKernelParameters -+ *out = make(map[string][]string, len(*in)) -+ for key, val := range *in { -+ var outVal []string -+ if val == nil { -+ (*out)[key] = nil -+ } else { -+ in, out := &val, &outVal -+ *out = make([]string, len(*in)) -+ copy(*out, *in) -+ } -+ (*out)[key] = outVal -+ } -+ } -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketBootSettings. -+func (in *BottlerocketBootSettings) DeepCopy() *BottlerocketBootSettings { -+ if in == nil { -+ return nil -+ } -+ out := new(BottlerocketBootSettings) -+ in.DeepCopyInto(out) -+ return out -+} -+ - // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. - func (in *BottlerocketBootstrap) DeepCopyInto(out *BottlerocketBootstrap) { - *out = *in -@@ -282,6 +312,11 @@ func (in *BottlerocketSettings) DeepCopyInto(out *BottlerocketSettings) { - *out = new(BottlerocketKernelSettings) - (*in).DeepCopyInto(*out) - } -+ if in.Boot != nil { -+ in, out := &in.Boot, &out.Boot -+ *out = new(BottlerocketBootSettings) -+ (*in).DeepCopyInto(*out) -+ } - } - - // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new BottlerocketSettings. -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -index 605e3b55d..883c662ce 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -@@ -1241,6 +1241,17 @@ spec: - description: Bottlerocket holds configuration for certain bottlerocket - settings. This is only for bottlerocket. - properties: -+ boot: -+ description: Boot holds the boot-related settings for bottlerocket -+ nodes -+ properties: -+ bootKernelParameters: -+ additionalProperties: -+ items: -+ type: string -+ type: array -+ type: object -+ type: object - kernel: - description: KernelSettings contains additional kernel settings - for Bottlerocket. -@@ -2070,6 +2081,17 @@ spec: - description: Bottlerocket holds configuration for certain bottlerocket - settings. This is only for bottlerocket. - properties: -+ boot: -+ description: Boot holds the boot-related settings for bottlerocket -+ nodes -+ properties: -+ bootKernelParameters: -+ additionalProperties: -+ items: -+ type: string -+ type: array -+ type: object -+ type: object - kernel: - description: KernelSettings contains additional kernel settings - for Bottlerocket. -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -index 5227b7333..61477b8f9 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -@@ -1274,6 +1274,17 @@ spec: - description: Bottlerocket holds configuration for certain - bottlerocket settings. This is only for bottlerocket. - properties: -+ boot: -+ description: Boot holds the boot-related settings -+ for bottlerocket nodes -+ properties: -+ bootKernelParameters: -+ additionalProperties: -+ items: -+ type: string -+ type: array -+ type: object -+ type: object - kernel: - description: KernelSettings contains additional kernel - settings for Bottlerocket. -@@ -2160,6 +2171,17 @@ spec: - description: Bottlerocket holds configuration for certain - bottlerocket settings. This is only for bottlerocket. - properties: -+ boot: -+ description: Boot holds the boot-related settings -+ for bottlerocket nodes -+ properties: -+ bootKernelParameters: -+ additionalProperties: -+ items: -+ type: string -+ type: array -+ type: object -+ type: object - kernel: - description: KernelSettings contains additional kernel - settings for Bottlerocket. -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -index a23a43668..901db1cb7 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -@@ -119,6 +119,15 @@ time-servers = [{{stringsJoin .NTPServers ", " }}] - [settings.kernel.sysctl] - {{.SysctlSettings}} - {{- end -}} -+` -+ -+ bootSettingsTemplate = `{{ define "bootSettings" -}} -+[settings.boot] -+reboot-to-reconcile = true -+ -+[settings.boot.kernel-parameters] -+{{.BootKernel}} -+{{- end -}} - ` - - bottlerocketNodeInitSettingsTemplate = `{{template "hostContainerSlice" .}} -@@ -159,5 +168,9 @@ time-servers = [{{stringsJoin .NTPServers ", " }}] - {{- if (ne .SysctlSettings "")}} - {{template "sysctlSettingsTemplate" .}} - {{- end -}} -+ -+{{- if .BootKernel}} -+{{template "bootSettings" .}} -+{{- end -}} - ` - ) -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -index fdc60204d..5846524be 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -@@ -279,6 +279,36 @@ hostname = "hostname" - [settings.kernel.sysctl] - "foo" = "bar" - "abc" = "def" -+` -+ -+ BootSettingsUserData = ` -+[settings.host-containers.admin] -+enabled = true -+superpowered = true -+source = "ADMIN_REPO:ADMIN_TAG" -+user-data = "CnsKCSJzc2giOiB7CgkJImF1dGhvcml6ZWQta2V5cyI6IFsic3NoLXJzYSBBQUEuLi4iXQoJfQp9" -+[settings.host-containers.kubeadm-bootstrap] -+enabled = true -+superpowered = true -+source = "BOOTSTRAP_REPO:BOOTSTRAP_TAG" -+user-data = "Qk9UVExFUk9DS0VUX0JPT1RTVFJBUF9VU0VSREFUQQ==" -+ -+[settings.kubernetes] -+cluster-domain = "cluster.local" -+standalone-mode = true -+authentication-mode = "tls" -+server-tls-bootstrap = false -+pod-infra-container-image = "PAUSE_REPO:PAUSE_TAG" -+provider-id = "PROVIDERID" -+ -+[settings.network] -+hostname = "hostname" -+[settings.boot] -+reboot-to-reconcile = true -+ -+[settings.boot.kernel-parameters] -+"abc" = ["def","123"] -+"foo" = ["bar"] - ` - ) - -@@ -513,10 +543,37 @@ func TestGetBottlerocketNodeUserData(t *testing.T) { - }, - output: kernelSettingsUserData, - }, -+ { -+ name: "with boot settings", -+ config: &BottlerocketConfig{ -+ BottlerocketAdmin: brAdmin, -+ BottlerocketBootstrap: brBootstrap, -+ Hostname: hostname, -+ Pause: pause, -+ KubeletExtraArgs: map[string]string{ -+ "provider-id": "PROVIDERID", -+ }, -+ BottlerocketSettings: &bootstrapv1.BottlerocketSettings{ -+ Boot: &bootstrapv1.BottlerocketBootSettings{ -+ BootKernelParameters: map[string][]string{ -+ "abc": { -+ "def", -+ "123", -+ }, -+ "foo": { -+ "bar", -+ }, -+ }, -+ }, -+ }, -+ }, -+ output: BootSettingsUserData, -+ }, - } - for _, testcase := range testcases { - t.Run(testcase.name, func(t *testing.T) { - b, err := getBottlerocketNodeUserData(brBootstrapUserdata, users, testcase.config) -+ println(string(b)) - g.Expect(err).NotTo(HaveOccurred()) - g.Expect(string(b)).To(Equal(testcase.output)) - }) -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -index afd854f1c..7b7131829 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -@@ -57,6 +57,7 @@ type BottlerocketSettingsInput struct { - AllowedUnsafeSysctls []string - ClusterDNSIPs []string - MaxPods int -+ BootKernel string - HostContainers []bootstrapv1.BottlerocketHostContainer - BootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer - SysctlSettings string -@@ -160,6 +161,9 @@ func generateNodeUserData(kind string, tpl string, data interface{}) ([]byte, er - if _, err := tm.Parse(sysctlSettingsTemplate); err != nil { - return nil, errors.Wrapf(err, "failed to parse sysctl settings %s template", kind) - } -+ if _, err := tm.Parse(bootSettingsTemplate); err != nil { -+ return nil, errors.Wrapf(err, "failed to parse boot settings %s template", kind) -+ } - t, err := tm.Parse(tpl) - if err != nil { - return nil, errors.Wrapf(err, "failed to parse %s template", kind) -@@ -257,6 +261,10 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot - bottlerocketInput.SysctlSettings = parseSysctlSettings(config.BottlerocketSettings.Kernel.SysctlSettings) - } - -+ if config.BottlerocketSettings.Boot != nil { -+ bottlerocketInput.BootKernel = parseBootSettings(config.BottlerocketSettings.Boot.BootKernelParameters) -+ } -+ - } - - return generateNodeUserData("InitBottlerocketNode", bottlerocketNodeInitSettingsTemplate, bottlerocketInput) -@@ -315,6 +323,22 @@ func parseSysctlSettings(sysctlSettings map[string]string) string { - return sysctlSettingsToml - } - -+func parseBootSettings(bootSettings map[string][]string) string { -+ bootSettingsToml := "" -+ for key, value := range bootSettings { -+ var values []string -+ if len(value) != 0 { -+ for _, val := range value { -+ quotedVal := "\"" + val + "\"" -+ values = append(values, quotedVal) -+ } -+ } -+ keyVal := strings.Join(values, ",") -+ bootSettingsToml += fmt.Sprintf("\"%v\" = [%v]\n", key, keyVal) -+ } -+ return bootSettingsToml -+} -+ - // Parses through all the users and return list of all user's authorized ssh keys - func getAllAuthorizedKeys(users []bootstrapv1.User) string { - var sshAuthorizedKeys []string -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -index f811f9a25..eb23db260 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -@@ -1519,6 +1519,17 @@ spec: - description: Bottlerocket holds configuration for certain - bottlerocket settings. This is only for bottlerocket. - properties: -+ boot: -+ description: Boot holds the boot-related settings for -+ bottlerocket nodes -+ properties: -+ bootKernelParameters: -+ additionalProperties: -+ items: -+ type: string -+ type: array -+ type: object -+ type: object - kernel: - description: KernelSettings contains additional kernel - settings for Bottlerocket. -@@ -2383,6 +2394,17 @@ spec: - description: Bottlerocket holds configuration for certain - bottlerocket settings. This is only for bottlerocket. - properties: -+ boot: -+ description: Boot holds the boot-related settings for -+ bottlerocket nodes -+ properties: -+ bootKernelParameters: -+ additionalProperties: -+ items: -+ type: string -+ type: array -+ type: object -+ type: object - kernel: - description: KernelSettings contains additional kernel - settings for Bottlerocket. -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -index 61a9c61db..0ffbde066 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -@@ -1473,6 +1473,17 @@ spec: - certain bottlerocket settings. This is only for - bottlerocket. - properties: -+ boot: -+ description: Boot holds the boot-related settings -+ for bottlerocket nodes -+ properties: -+ bootKernelParameters: -+ additionalProperties: -+ items: -+ type: string -+ type: array -+ type: object -+ type: object - kernel: - description: KernelSettings contains additional - kernel settings for Bottlerocket. -@@ -2397,6 +2408,17 @@ spec: - certain bottlerocket settings. This is only for - bottlerocket. - properties: -+ boot: -+ description: Boot holds the boot-related settings -+ for bottlerocket nodes -+ properties: -+ bootKernelParameters: -+ additionalProperties: -+ items: -+ type: string -+ type: array -+ type: object -+ type: object - kernel: - description: KernelSettings contains additional - kernel settings for Bottlerocket. -diff --git a/internal/controllers/machine/machine_controller_phases.go b/internal/controllers/machine/machine_controller_phases.go -index e17031c99..4ad429a45 100644 ---- a/internal/controllers/machine/machine_controller_phases.go -+++ b/internal/controllers/machine/machine_controller_phases.go -@@ -19,9 +19,10 @@ package machine - import ( - "context" - "fmt" -- "sigs.k8s.io/controller-runtime/pkg/client" - "time" - -+ "sigs.k8s.io/controller-runtime/pkg/client" -+ - "github.com/pkg/errors" - corev1 "k8s.io/api/core/v1" - apierrors "k8s.io/apimachinery/pkg/api/errors" -@@ -378,7 +379,7 @@ func (r *Reconciler) reconcileInfrastructure(ctx context.Context, s *scope) (ctr - }, - }, - Data: map[string][]byte{ -- "address": []byte(machineIP), -+ "address": []byte(machineIP), - "clientUrls": []byte(fmt.Sprintf("https://%v:2379", machineIP)), - }, - Type: clusterv1.ClusterSecretType, --- -2.39.3 (Apple Git-145) - diff --git a/projects/kubernetes-sigs/cluster-api/patches/0032-CAPI-Move-Cluster-Filter.patch b/projects/kubernetes-sigs/cluster-api/patches/0030-CAPI-Move-Cluster-Filter.patch similarity index 99% rename from projects/kubernetes-sigs/cluster-api/patches/0032-CAPI-Move-Cluster-Filter.patch rename to projects/kubernetes-sigs/cluster-api/patches/0030-CAPI-Move-Cluster-Filter.patch index 7e97f386b7..c44b7d04dc 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0032-CAPI-Move-Cluster-Filter.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0030-CAPI-Move-Cluster-Filter.patch @@ -1,7 +1,7 @@ -From 9fd20f816c585c26b83c3bd18fd9cfcd36609941 Mon Sep 17 00:00:00 2001 +From 8cdc5a1a602948c5393358d38147549b50c75e07 Mon Sep 17 00:00:00 2001 From: Vignesh Goutham Ganesh Date: Tue, 16 May 2023 11:03:09 -0500 -Subject: [PATCH 32/40] CAPI Move Cluster Filter +Subject: [PATCH 30/40] CAPI Move Cluster Filter Signed-off-by: Vignesh Goutham Ganesh --- @@ -533,5 +533,5 @@ index c8316b376..7ba98b264 100644 }) } -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0031-Add-support-for-custom-cert-bundles-in-BR-21.patch b/projects/kubernetes-sigs/cluster-api/patches/0031-Add-support-for-custom-cert-bundles-in-BR-21.patch deleted file mode 100644 index 911cb15ed1..0000000000 --- a/projects/kubernetes-sigs/cluster-api/patches/0031-Add-support-for-custom-cert-bundles-in-BR-21.patch +++ /dev/null @@ -1,569 +0,0 @@ -From fdf7bab4c9309dfa96200dd12b33ad5b0b48afec Mon Sep 17 00:00:00 2001 -From: ahreehong <46465244+ahreehong@users.noreply.github.com> -Date: Fri, 19 May 2023 16:29:08 -0400 -Subject: [PATCH 31/40] Add support for custom cert bundles in BR (#21) - -* add support for custom cert bundles br - -* take in non base-64 encoded data for cert - -Signed-off-by: Ahree Hong ---- - .../api/v1alpha4/zz_generated.conversion.go | 2 + - .../kubeadm/api/v1beta1/kubeadm_types.go | 17 ++++++ - .../api/v1beta1/zz_generated.deepcopy.go | 25 +++++++++ - ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 32 +++++++++++ - ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 34 ++++++++++++ - .../internal/bottlerocket/bootstrap.go | 16 ++++++ - .../internal/bottlerocket/bootstrap_test.go | 53 +++++++++++++++++++ - .../internal/bottlerocket/bottlerocket.go | 14 +++++ - .../controllers/kubeadmconfig_controller.go | 9 ++++ - .../zz_generated.conversion.go | 2 + - .../zz_generated.conversion.go | 2 + - ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 32 +++++++++++ - ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 34 ++++++++++++ - 13 files changed, 272 insertions(+) - -diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -index 43971cb70..d43c45841 100644 ---- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -@@ -731,6 +731,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_v1alpha4_ClusterConfiguration(i - // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type - // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type -+ // WARNING: in.CertBundles requires manual conversion: does not exist in peer-type - return nil - } - -@@ -1139,6 +1140,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_v1alpha4_JoinConfiguration(in *v1b - // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type - // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type -+ // WARNING: in.CertBundles requires manual conversion: does not exist in peer-type - return nil - } - -diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -index 434d2c088..ed965709a 100644 ---- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -+++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -@@ -190,6 +190,10 @@ type ClusterConfiguration struct { - // This is only for bottlerocket. - // +optional - Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` -+ -+ // CertBundles holds additional trusted cert bundles. -+ // +optional -+ CertBundles []CertBundle `json:"certBundles,omitempty"` - } - - // BottlerocketSettings define bottlerocket settings that can be configured on bottlerocket nodes. -@@ -621,6 +625,10 @@ type JoinConfiguration struct { - // This is only for bottlerocket. - // +optional - Bottlerocket *BottlerocketSettings `json:"bottlerocket,omitempty"` -+ -+ // CertBundles holds additional trusted cert bundles. -+ // +optional -+ CertBundles []CertBundle `json:"certBundles,omitempty"` - } - - // BottlerocketHostContainer describes a host image for Bottlerocket -@@ -661,6 +669,15 @@ type BottlerocketBootstrapContainer struct { - UserData string `json:"userData,omitempty"` - } - -+// CertBundle holds the cert data. -+type CertBundle struct { -+ // Name is the name of the cert bundle. -+ Name string `json:"name"` -+ -+ // Data is the actual cert. -+ Data string `json:"data"` -+} -+ - // JoinControlPlane contains elements describing an additional control plane instance to be deployed on the joining node. - type JoinControlPlane struct { - // LocalAPIEndpoint represents the endpoint of the API server instance to be deployed on this node. -diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -index 09dcc431f..af85cfd21 100644 ---- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -+++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -@@ -329,6 +329,21 @@ func (in *BottlerocketSettings) DeepCopy() *BottlerocketSettings { - return out - } - -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *CertBundle) DeepCopyInto(out *CertBundle) { -+ *out = *in -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CertBundle. -+func (in *CertBundle) DeepCopy() *CertBundle { -+ if in == nil { -+ return nil -+ } -+ out := new(CertBundle) -+ in.DeepCopyInto(out) -+ return out -+} -+ - // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. - func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { - *out = *in -@@ -367,6 +382,11 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { - *out = new(BottlerocketSettings) - (*in).DeepCopyInto(*out) - } -+ if in.CertBundles != nil { -+ in, out := &in.CertBundles, &out.CertBundles -+ *out = make([]CertBundle, len(*in)) -+ copy(*out, *in) -+ } - } - - // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ClusterConfiguration. -@@ -801,6 +821,11 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { - *out = new(BottlerocketSettings) - (*in).DeepCopyInto(*out) - } -+ if in.CertBundles != nil { -+ in, out := &in.CertBundles, &out.CertBundles -+ *out = make([]CertBundle, len(*in)) -+ copy(*out, *in) -+ } - } - - // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new JoinConfiguration. -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -index 883c662ce..9135db4f9 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -@@ -1414,6 +1414,22 @@ spec: - - superpowered - type: object - type: array -+ certBundles: -+ description: CertBundles holds additional trusted cert bundles. -+ items: -+ description: CertBundle holds the cert data. -+ properties: -+ data: -+ description: Data is the actual cert. -+ type: string -+ name: -+ description: Name is the name of the cert bundle. -+ type: string -+ required: -+ - data -+ - name -+ type: object -+ type: array - certificatesDir: - description: 'CertificatesDir specifies where to store or look - for all required certificates. NB: if not provided, this will -@@ -2260,6 +2276,22 @@ spec: - Defaults to "/etc/kubernetes/pki/ca.crt". TODO: revisit when - there is defaulting from k/k' - type: string -+ certBundles: -+ description: CertBundles holds additional trusted cert bundles. -+ items: -+ description: CertBundle holds the cert data. -+ properties: -+ data: -+ description: Data is the actual cert. -+ type: string -+ name: -+ description: Name is the name of the cert bundle. -+ type: string -+ required: -+ - data -+ - name -+ type: object -+ type: array - controlPlane: - description: ControlPlane defines the additional control plane - instance to be deployed on the joining node. If nil, no additional -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -index 61477b8f9..b097f1975 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -@@ -1457,6 +1457,23 @@ spec: - - superpowered - type: object - type: array -+ certBundles: -+ description: CertBundles holds additional trusted cert -+ bundles. -+ items: -+ description: CertBundle holds the cert data. -+ properties: -+ data: -+ description: Data is the actual cert. -+ type: string -+ name: -+ description: Name is the name of the cert bundle. -+ type: string -+ required: -+ - data -+ - name -+ type: object -+ type: array - certificatesDir: - description: 'CertificatesDir specifies where to store - or look for all required certificates. NB: if not provided, -@@ -2360,6 +2377,23 @@ spec: - and control-plane. Defaults to "/etc/kubernetes/pki/ca.crt". - TODO: revisit when there is defaulting from k/k' - type: string -+ certBundles: -+ description: CertBundles holds additional trusted cert -+ bundles. -+ items: -+ description: CertBundle holds the cert data. -+ properties: -+ data: -+ description: Data is the actual cert. -+ type: string -+ name: -+ description: Name is the name of the cert bundle. -+ type: string -+ required: -+ - data -+ - name -+ type: object -+ type: array - controlPlane: - description: ControlPlane defines the additional control - plane instance to be deployed on the joining node. If -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -index 901db1cb7..df222b943 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -@@ -128,6 +128,18 @@ reboot-to-reconcile = true - [settings.boot.kernel-parameters] - {{.BootKernel}} - {{- end -}} -+` -+ certsTemplate = `{{ define "certsSettings" -}} -+[settings.pki.{{.Name}}] -+data = "{{.Data}}" -+trusted = true -+{{- end -}} -+` -+ certBundlesSliceTemplate = `{{ define "certBundlesSlice" -}} -+{{- range $cBundle := .CertBundles }} -+{{template "certsSettings" $cBundle }} -+{{- end -}} -+{{- end -}} - ` - - bottlerocketNodeInitSettingsTemplate = `{{template "hostContainerSlice" .}} -@@ -172,5 +184,9 @@ reboot-to-reconcile = true - {{- if .BootKernel}} - {{template "bootSettings" .}} - {{- end -}} -+ -+{{- if .CertBundles}} -+{{template "certBundlesSlice" .}} -+{{- end -}} - ` - ) -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -index 5846524be..2ee2d942b 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -@@ -310,6 +310,36 @@ reboot-to-reconcile = true - "abc" = ["def","123"] - "foo" = ["bar"] - ` -+ -+ userDataWithCertBundle = ` -+[settings.host-containers.admin] -+enabled = true -+superpowered = true -+source = "ADMIN_REPO:ADMIN_TAG" -+user-data = "CnsKCSJzc2giOiB7CgkJImF1dGhvcml6ZWQta2V5cyI6IFsic3NoLXJzYSBBQUEuLi4iXQoJfQp9" -+[settings.host-containers.kubeadm-bootstrap] -+enabled = true -+superpowered = true -+source = "BOOTSTRAP_REPO:BOOTSTRAP_TAG" -+user-data = "Qk9UVExFUk9DS0VUX0JPT1RTVFJBUF9VU0VSREFUQQ==" -+ -+[settings.kubernetes] -+cluster-domain = "cluster.local" -+standalone-mode = true -+authentication-mode = "tls" -+server-tls-bootstrap = false -+pod-infra-container-image = "PAUSE_REPO:PAUSE_TAG" -+provider-id = "PROVIDERID" -+ -+[settings.network] -+hostname = "hostname" -+ -+[settings.pki.bundle1] -+data = "QUJDREVG" -+trusted = true -+[settings.pki.bundle2] -+data = "MTIzNDU2" -+trusted = true` - ) - - var ( -@@ -569,6 +599,29 @@ func TestGetBottlerocketNodeUserData(t *testing.T) { - }, - output: BootSettingsUserData, - }, -+ { -+ name: "with custom cert bundle settings", -+ config: &BottlerocketConfig{ -+ BottlerocketAdmin: brAdmin, -+ BottlerocketBootstrap: brBootstrap, -+ Hostname: hostname, -+ Pause: pause, -+ KubeletExtraArgs: map[string]string{ -+ "provider-id": "PROVIDERID", -+ }, -+ CertBundle: []bootstrapv1.CertBundle{ -+ { -+ Name: "bundle1", -+ Data: "ABCDEF", -+ }, -+ { -+ Name: "bundle2", -+ Data: "123456", -+ }, -+ }, -+ }, -+ output: userDataWithCertBundle, -+ }, - } - for _, testcase := range testcases { - t.Run(testcase.name, func(t *testing.T) { -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -index 7b7131829..ce796f206 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -@@ -37,6 +37,7 @@ type BottlerocketConfig struct { - BottlerocketCustomBootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer - NTPServers []string - Hostname string -+ CertBundle []bootstrapv1.CertBundle - RegistryMirrorCredentials - } - -@@ -61,6 +62,7 @@ type BottlerocketSettingsInput struct { - HostContainers []bootstrapv1.BottlerocketHostContainer - BootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer - SysctlSettings string -+ CertBundles []bootstrapv1.CertBundle - } - - // HostPath holds the path and type of a host path volume. -@@ -164,6 +166,12 @@ func generateNodeUserData(kind string, tpl string, data interface{}) ([]byte, er - if _, err := tm.Parse(bootSettingsTemplate); err != nil { - return nil, errors.Wrapf(err, "failed to parse boot settings %s template", kind) - } -+ if _, err := tm.Parse(certsTemplate); err != nil { -+ return nil, errors.Wrapf(err, "failed to parse certs %s template", kind) -+ } -+ if _, err := tm.Parse(certBundlesSliceTemplate); err != nil { -+ return nil, errors.Wrapf(err, "failed to parse cert bundles %s template", kind) -+ } - t, err := tm.Parse(tpl) - if err != nil { - return nil, errors.Wrapf(err, "failed to parse %s template", kind) -@@ -266,6 +274,12 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot - } - - } -+ if config.CertBundle != nil { -+ for _, cert := range config.CertBundle { -+ cert.Data = base64.StdEncoding.EncodeToString([]byte(cert.Data)) -+ bottlerocketInput.CertBundles = append(bottlerocketInput.CertBundles, cert) -+ } -+ } - - return generateNodeUserData("InitBottlerocketNode", bottlerocketNodeInitSettingsTemplate, bottlerocketInput) - } -diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -index b63a64589..4e8b7c5e0 100644 ---- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -+++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -@@ -509,6 +509,9 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex - if scope.Config.Spec.NTP != nil && scope.Config.Spec.NTP.Enabled != nil && *scope.Config.Spec.NTP.Enabled { - bottlerocketConfig.NTPServers = scope.Config.Spec.NTP.Servers - } -+ if scope.Config.Spec.ClusterConfiguration.CertBundles != nil { -+ bottlerocketConfig.CertBundle = scope.Config.Spec.ClusterConfiguration.CertBundles -+ } - } - - clusterdata, err := kubeadmtypes.MarshalClusterConfigurationForVersion(scope.Config.Spec.ClusterConfiguration, parsedVersion) -@@ -734,6 +737,9 @@ func (r *KubeadmConfigReconciler) joinWorker(ctx context.Context, scope *Scope) - if scope.Config.Spec.NTP != nil && scope.Config.Spec.NTP.Enabled != nil && *scope.Config.Spec.NTP.Enabled { - bottlerocketConfig.NTPServers = scope.Config.Spec.NTP.Servers - } -+ if scope.Config.Spec.JoinConfiguration.CertBundles != nil { -+ bottlerocketConfig.CertBundle = scope.Config.Spec.JoinConfiguration.CertBundles -+ } - bootstrapJoinData, err = bottlerocket.NewNode(nodeInput, bottlerocketConfig) - if err != nil { - scope.Error(err, "Failed to create a worker bottlerocket join configuration") -@@ -881,6 +887,9 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S - if scope.Config.Spec.NTP != nil && scope.Config.Spec.NTP.Enabled != nil && *scope.Config.Spec.NTP.Enabled { - bottlerocketConfig.NTPServers = scope.Config.Spec.NTP.Servers - } -+ if scope.Config.Spec.JoinConfiguration.CertBundles != nil { -+ bottlerocketConfig.CertBundle = scope.Config.Spec.JoinConfiguration.CertBundles -+ } - bootstrapJoinData, err = bottlerocket.NewJoinControlPlane(controlPlaneJoinInput, bottlerocketConfig) - if err != nil { - scope.Error(err, "Failed to generate cloud init for bottlerocket bootstrap control plane") -diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -index 8b1acbb57..3b12557c4 100644 ---- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -@@ -565,6 +565,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta2_ClusterConfigur - // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type - // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type -+ // WARNING: in.CertBundles requires manual conversion: does not exist in peer-type - return nil - } - -@@ -877,6 +878,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta2_JoinConfiguration( - // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type - // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type -+ // WARNING: in.CertBundles requires manual conversion: does not exist in peer-type - return nil - } - -diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -index c613bdd12..6d812f516 100644 ---- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -@@ -569,6 +569,7 @@ func autoConvert_v1beta1_ClusterConfiguration_To_upstreamv1beta3_ClusterConfigur - // WARNING: in.BottlerocketHostContainers requires manual conversion: does not exist in peer-type - // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type -+ // WARNING: in.CertBundles requires manual conversion: does not exist in peer-type - return nil - } - -@@ -869,6 +870,7 @@ func autoConvert_v1beta1_JoinConfiguration_To_upstreamv1beta3_JoinConfiguration( - // WARNING: in.BottlerocketCustomHostContainers requires manual conversion: does not exist in peer-type - // WARNING: in.BottlerocketCustomBootstrapContainers requires manual conversion: does not exist in peer-type - // WARNING: in.Bottlerocket requires manual conversion: does not exist in peer-type -+ // WARNING: in.CertBundles requires manual conversion: does not exist in peer-type - return nil - } - -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -index eb23db260..86f387bb9 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -@@ -1700,6 +1700,22 @@ spec: - - superpowered - type: object - type: array -+ certBundles: -+ description: CertBundles holds additional trusted cert bundles. -+ items: -+ description: CertBundle holds the cert data. -+ properties: -+ data: -+ description: Data is the actual cert. -+ type: string -+ name: -+ description: Name is the name of the cert bundle. -+ type: string -+ required: -+ - data -+ - name -+ type: object -+ type: array - certificatesDir: - description: 'CertificatesDir specifies where to store or - look for all required certificates. NB: if not provided, -@@ -2581,6 +2597,22 @@ spec: - control-plane. Defaults to "/etc/kubernetes/pki/ca.crt". - TODO: revisit when there is defaulting from k/k' - type: string -+ certBundles: -+ description: CertBundles holds additional trusted cert bundles. -+ items: -+ description: CertBundle holds the cert data. -+ properties: -+ data: -+ description: Data is the actual cert. -+ type: string -+ name: -+ description: Name is the name of the cert bundle. -+ type: string -+ required: -+ - data -+ - name -+ type: object -+ type: array - controlPlane: - description: ControlPlane defines the additional control plane - instance to be deployed on the joining node. If nil, no -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -index 0ffbde066..9a2228488 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -@@ -1666,6 +1666,23 @@ spec: - - superpowered - type: object - type: array -+ certBundles: -+ description: CertBundles holds additional trusted -+ cert bundles. -+ items: -+ description: CertBundle holds the cert data. -+ properties: -+ data: -+ description: Data is the actual cert. -+ type: string -+ name: -+ description: Name is the name of the cert bundle. -+ type: string -+ required: -+ - data -+ - name -+ type: object -+ type: array - certificatesDir: - description: 'CertificatesDir specifies where to store - or look for all required certificates. NB: if not -@@ -2607,6 +2624,23 @@ spec: - and control-plane. Defaults to "/etc/kubernetes/pki/ca.crt". - TODO: revisit when there is defaulting from k/k' - type: string -+ certBundles: -+ description: CertBundles holds additional trusted -+ cert bundles. -+ items: -+ description: CertBundle holds the cert data. -+ properties: -+ data: -+ description: Data is the actual cert. -+ type: string -+ name: -+ description: Name is the name of the cert bundle. -+ type: string -+ required: -+ - data -+ - name -+ type: object -+ type: array - controlPlane: - description: ControlPlane defines the additional control - plane instance to be deployed on the joining node. --- -2.39.3 (Apple Git-145) - diff --git a/projects/kubernetes-sigs/cluster-api/patches/0033-Move-objects-with-force-move-label-and-no-cluster-te.patch b/projects/kubernetes-sigs/cluster-api/patches/0031-Move-objects-with-force-move-label-and-no-cluster-te.patch similarity index 95% rename from projects/kubernetes-sigs/cluster-api/patches/0033-Move-objects-with-force-move-label-and-no-cluster-te.patch rename to projects/kubernetes-sigs/cluster-api/patches/0031-Move-objects-with-force-move-label-and-no-cluster-te.patch index a42f6e15df..7db681e55d 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0033-Move-objects-with-force-move-label-and-no-cluster-te.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0031-Move-objects-with-force-move-label-and-no-cluster-te.patch @@ -1,7 +1,7 @@ -From 7ceec3ac63dae6d8e98728bf8e073695278df7b4 Mon Sep 17 00:00:00 2001 +From bf669819e8578a91a2b7062741a8a526ee1d9afd Mon Sep 17 00:00:00 2001 From: Vignesh Goutham Ganesh Date: Tue, 30 May 2023 10:14:31 -0500 -Subject: [PATCH 33/40] Move objects with force move label and no cluster +Subject: [PATCH 31/40] Move objects with force move label and no cluster tenants Signed-off-by: Vignesh Goutham Ganesh @@ -84,5 +84,5 @@ index 8586ef19c..2b92ba3bc 100644 for _, tt := range tests { -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0034-allow-registry-mirror-configurations-to-be-mutable-f.patch b/projects/kubernetes-sigs/cluster-api/patches/0032-allow-registry-mirror-configurations-to-be-mutable-f.patch similarity index 97% rename from projects/kubernetes-sigs/cluster-api/patches/0034-allow-registry-mirror-configurations-to-be-mutable-f.patch rename to projects/kubernetes-sigs/cluster-api/patches/0032-allow-registry-mirror-configurations-to-be-mutable-f.patch index ca0c3e0f4e..3a13cac526 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0034-allow-registry-mirror-configurations-to-be-mutable-f.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0032-allow-registry-mirror-configurations-to-be-mutable-f.patch @@ -1,7 +1,7 @@ -From 8af6a7fb2e4093d3fbd7dfeea215705a093aa9af Mon Sep 17 00:00:00 2001 +From 971c67418f5db0575cdd63785bbb50f9872e7963 Mon Sep 17 00:00:00 2001 From: Cavaughn Browne Date: Thu, 20 Jul 2023 11:05:49 -0500 -Subject: [PATCH 34/40] allow registry mirror configurations to be mutable for +Subject: [PATCH 32/40] allow registry mirror configurations to be mutable for BR --- @@ -107,5 +107,5 @@ index 0fb9025d1..efccae0a0 100644 for _, tt := range tests { -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0035-Add-support-for-external-etcd-machines-in-Kind-mappe.patch b/projects/kubernetes-sigs/cluster-api/patches/0033-Add-support-for-external-etcd-machines-in-Kind-mappe.patch similarity index 98% rename from projects/kubernetes-sigs/cluster-api/patches/0035-Add-support-for-external-etcd-machines-in-Kind-mappe.patch rename to projects/kubernetes-sigs/cluster-api/patches/0033-Add-support-for-external-etcd-machines-in-Kind-mappe.patch index a6dfcc27f7..e34d5c38e9 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0035-Add-support-for-external-etcd-machines-in-Kind-mappe.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0033-Add-support-for-external-etcd-machines-in-Kind-mappe.patch @@ -1,7 +1,7 @@ -From dc582ea4f2353b8f7ae417a922cd32005c002b90 Mon Sep 17 00:00:00 2001 +From 615140b4beffdc72afb1ff8a0a635d26487701e8 Mon Sep 17 00:00:00 2001 From: Prow Bot Date: Wed, 16 Aug 2023 19:58:01 -0700 -Subject: [PATCH 35/40] Add support for external etcd machines in Kind mapper +Subject: [PATCH 33/40] Add support for external etcd machines in Kind mapper --- .../client/cluster/objectgraph_test.go | 2 +- @@ -190,5 +190,5 @@ index 96c9df5ed..3a5090e0b 100644 kindMapping := kind.GetMapping(semVer, image) -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0036-disable-cgroupns-private-to-fix-AL2.patch b/projects/kubernetes-sigs/cluster-api/patches/0034-disable-cgroupns-private-to-fix-AL2.patch similarity index 84% rename from projects/kubernetes-sigs/cluster-api/patches/0036-disable-cgroupns-private-to-fix-AL2.patch rename to projects/kubernetes-sigs/cluster-api/patches/0034-disable-cgroupns-private-to-fix-AL2.patch index 2abcb8fc59..57cea847d8 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0036-disable-cgroupns-private-to-fix-AL2.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0034-disable-cgroupns-private-to-fix-AL2.patch @@ -1,14 +1,14 @@ -From 00fe1b17bb4c89068658549424ae3c09850e05a0 Mon Sep 17 00:00:00 2001 +From 9ad487081cefcfc37bba3dc5c0c7798adb2dfbd0 Mon Sep 17 00:00:00 2001 From: Jackson West Date: Sat, 19 Aug 2023 09:35:39 -0500 -Subject: [PATCH 36/40] disable cgroupns=private to fix AL2 +Subject: [PATCH 34/40] disable cgroupns=private to fix AL2 --- test/infrastructure/container/docker.go | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/test/infrastructure/container/docker.go b/test/infrastructure/container/docker.go -index f2de71416..e06e2f3fb 100644 +index fbf988762..38e5056c8 100644 --- a/test/infrastructure/container/docker.go +++ b/test/infrastructure/container/docker.go @@ -41,7 +41,6 @@ import ( @@ -19,7 +19,7 @@ index f2de71416..e06e2f3fb 100644 ) const ( -@@ -411,9 +410,11 @@ func (d *dockerRuntime) RunContainer(ctx context.Context, runConfig *RunContaine +@@ -410,9 +409,11 @@ func (d *dockerRuntime) RunContainer(ctx context.Context, runConfig *RunContaine networkConfig := network.NetworkingConfig{} // NOTE: starting from Kind 0.20 kind requires CgroupnsMode to be set to private. @@ -35,5 +35,5 @@ index f2de71416..e06e2f3fb 100644 if runConfig.IPFamily == clusterv1.IPv6IPFamily || runConfig.IPFamily == clusterv1.DualStackIPFamily { hostConfig.Sysctls = map[string]string{ -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0037-Add-support-for-in-place-upgrade-in-KCP.patch b/projects/kubernetes-sigs/cluster-api/patches/0035-Add-support-for-in-place-upgrade-in-KCP.patch similarity index 97% rename from projects/kubernetes-sigs/cluster-api/patches/0037-Add-support-for-in-place-upgrade-in-KCP.patch rename to projects/kubernetes-sigs/cluster-api/patches/0035-Add-support-for-in-place-upgrade-in-KCP.patch index daa43d4c4e..af596a3296 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0037-Add-support-for-in-place-upgrade-in-KCP.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0035-Add-support-for-in-place-upgrade-in-KCP.patch @@ -1,7 +1,7 @@ -From 4d185489b99ee1bba850f7f1a829cd7a7d26af79 Mon Sep 17 00:00:00 2001 +From b683bc9eecdb0971840f3b8fbe3f3b967614676b Mon Sep 17 00:00:00 2001 From: Abhinav Pandey Date: Wed, 17 Jan 2024 09:28:18 -0800 -Subject: [PATCH 37/40] Add support for in-place upgrade in KCP +Subject: [PATCH 35/40] Add support for in-place upgrade in KCP --- .../kubeadm/api/v1beta1/kubeadm_control_plane_types.go | 8 ++++++++ @@ -101,5 +101,5 @@ index 772d1409d..39d22a6a4 100644 ) } -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0038-Add-support-for-in-place-upgrades-in-MachineDeployme.patch b/projects/kubernetes-sigs/cluster-api/patches/0036-Add-support-for-in-place-upgrades-in-MachineDeployme.patch similarity index 82% rename from projects/kubernetes-sigs/cluster-api/patches/0038-Add-support-for-in-place-upgrades-in-MachineDeployme.patch rename to projects/kubernetes-sigs/cluster-api/patches/0036-Add-support-for-in-place-upgrades-in-MachineDeployme.patch index df0611bd23..d332abdc1e 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0038-Add-support-for-in-place-upgrades-in-MachineDeployme.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0036-Add-support-for-in-place-upgrades-in-MachineDeployme.patch @@ -1,11 +1,10 @@ -From 92f5bee014540aeef48be525859bbd01a69f9cd8 Mon Sep 17 00:00:00 2001 +From 2446085f27f564efd79dc9a216cb0a54714831b7 Mon Sep 17 00:00:00 2001 From: Abhinav Pandey Date: Wed, 24 Jan 2024 00:00:03 -0800 -Subject: [PATCH 38/40] Add support for in-place upgrades in MachineDeployments +Subject: [PATCH 36/40] Add support for in-place upgrades in MachineDeployments --- api/v1beta1/machinedeployment_types.go | 11 +- - .../api/v1beta1/zz_generated.deepcopy.go | 3 +- .../cluster.x-k8s.io_clusterclasses.yaml | 1 + .../crd/bases/cluster.x-k8s.io_clusters.yaml | 1 + .../cluster.x-k8s.io_machinedeployments.yaml | 1 + @@ -13,8 +12,7 @@ Subject: [PATCH 38/40] Add support for in-place upgrades in MachineDeployments .../machinedeployment_inplace.go | 44 +++++++ .../machinedeployment_inplace_test.go | 110 ++++++++++++++++++ .../machinedeployment/mdutil/util.go | 2 + - .../test/builder/zz_generated.deepcopy.go | 23 ++++ - 10 files changed, 198 insertions(+), 2 deletions(-) + 8 files changed, 173 insertions(+), 1 deletion(-) create mode 100644 internal/controllers/machinedeployment/machinedeployment_inplace.go create mode 100644 internal/controllers/machinedeployment/machinedeployment_inplace_test.go @@ -54,20 +52,6 @@ index 13a023d07..c55d17b6b 100644 // +optional Type MachineDeploymentStrategyType `json:"type,omitempty"` -diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -index af85cfd21..9fefdcb62 100644 ---- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -+++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -@@ -169,7 +169,8 @@ func (in *BottlerocketBootSettings) DeepCopyInto(out *BottlerocketBootSettings) - if val == nil { - (*out)[key] = nil - } else { -- in, out := &val, &outVal -+ inVal := (*in)[key] -+ in, out := &inVal, &outVal - *out = make([]string, len(*in)) - copy(*out, *in) - } diff --git a/config/crd/bases/cluster.x-k8s.io_clusterclasses.yaml b/config/crd/bases/cluster.x-k8s.io_clusterclasses.yaml index 34823e44b..328bd1c7c 100644 --- a/config/crd/bases/cluster.x-k8s.io_clusterclasses.yaml @@ -81,10 +65,10 @@ index 34823e44b..328bd1c7c 100644 type: object template: diff --git a/config/crd/bases/cluster.x-k8s.io_clusters.yaml b/config/crd/bases/cluster.x-k8s.io_clusters.yaml -index ab514c177..c99cdf68d 100644 +index a10bee3ce..863caf281 100644 --- a/config/crd/bases/cluster.x-k8s.io_clusters.yaml +++ b/config/crd/bases/cluster.x-k8s.io_clusters.yaml -@@ -1171,6 +1171,7 @@ spec: +@@ -1477,6 +1477,7 @@ spec: enum: - RollingUpdate - OnDelete @@ -93,7 +77,7 @@ index ab514c177..c99cdf68d 100644 type: object variables: diff --git a/config/crd/bases/cluster.x-k8s.io_machinedeployments.yaml b/config/crd/bases/cluster.x-k8s.io_machinedeployments.yaml -index 8abaa5ec1..e3319661c 100644 +index 5b9790178..98c907371 100644 --- a/config/crd/bases/cluster.x-k8s.io_machinedeployments.yaml +++ b/config/crd/bases/cluster.x-k8s.io_machinedeployments.yaml @@ -703,6 +703,7 @@ spec: @@ -298,47 +282,6 @@ index 2cf9d3427..203cd90f8 100644 default: return 0, fmt.Errorf("failed to compute replicas: deployment strategy %v isn't supported", deployment.Spec.Strategy.Type) } -diff --git a/internal/test/builder/zz_generated.deepcopy.go b/internal/test/builder/zz_generated.deepcopy.go -index 4ca1c64ca..64e72d45b 100644 ---- a/internal/test/builder/zz_generated.deepcopy.go -+++ b/internal/test/builder/zz_generated.deepcopy.go -@@ -95,6 +95,10 @@ func (in *ClusterBuilder) DeepCopyInto(out *ClusterBuilder) { - in, out := &in.controlPlane, &out.controlPlane - *out = (*in).DeepCopy() - } -+ if in.managedEtcd != nil { -+ in, out := &in.managedEtcd, &out.managedEtcd -+ *out = (*in).DeepCopy() -+ } - if in.network != nil { - in, out := &in.network, &out.network - *out = new(v1beta1.ClusterNetwork) -@@ -274,6 +278,25 @@ func (in *ControlPlaneTemplateBuilder) DeepCopy() *ControlPlaneTemplateBuilder { - return out - } - -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *EtcdPlaneBuilder) DeepCopyInto(out *EtcdPlaneBuilder) { -+ *out = *in -+ if in.obj != nil { -+ in, out := &in.obj, &out.obj -+ *out = (*in).DeepCopy() -+ } -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new EtcdPlaneBuilder. -+func (in *EtcdPlaneBuilder) DeepCopy() *EtcdPlaneBuilder { -+ if in == nil { -+ return nil -+ } -+ out := new(EtcdPlaneBuilder) -+ in.DeepCopyInto(out) -+ return out -+} -+ - // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. - func (in *InfrastructureClusterBuilder) DeepCopyInto(out *InfrastructureClusterBuilder) { - *out = *in -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0037-Adding-support-for-multiple-registry-mirrors-in-bott.patch b/projects/kubernetes-sigs/cluster-api/patches/0037-Adding-support-for-multiple-registry-mirrors-in-bott.patch new file mode 100644 index 0000000000..9fce469f50 --- /dev/null +++ b/projects/kubernetes-sigs/cluster-api/patches/0037-Adding-support-for-multiple-registry-mirrors-in-bott.patch @@ -0,0 +1,1370 @@ +From d7aa8cb0b30ac47ada8109ace606567240ad29d1 Mon Sep 17 00:00:00 2001 +From: Aravind Ramalingam +Date: Mon, 22 Jan 2024 12:47:26 -0800 +Subject: [PATCH 37/40] Adding support for multiple registry mirrors in + bottlerocket + +--- + .../kubeadm/api/v1alpha4/kubeadm_types.go | 15 +++ + .../api/v1alpha4/zz_generated.conversion.go | 34 +++++ + .../api/v1alpha4/zz_generated.deepcopy.go | 31 ++++- + .../kubeadm/api/v1beta1/kubeadm_types.go | 15 +++ + .../api/v1beta1/zz_generated.deepcopy.go | 31 ++++- + ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 114 ++++++++++++++++ + ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 126 ++++++++++++++++++ + .../internal/bottlerocket/bootstrap.go | 20 ++- + .../internal/bottlerocket/bootstrap_test.go | 72 +++++++++- + .../internal/bottlerocket/bottlerocket.go | 44 ++++-- + .../controllers/kubeadmconfig_controller.go | 12 +- + .../kubeadm/types/upstreamv1beta1/types.go | 15 +++ + .../zz_generated.conversion.go | 34 +++++ + .../upstreamv1beta1/zz_generated.deepcopy.go | 31 ++++- + .../zz_generated.conversion.go | 1 + + .../zz_generated.conversion.go | 1 + + .../cluster.x-k8s.io_machinedeployments.yaml | 2 +- + ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 126 ++++++++++++++++++ + ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 88 ++++++++++++ + 19 files changed, 783 insertions(+), 29 deletions(-) + +diff --git a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +index 3d43cae72..ab4ae1aa7 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1alpha4/kubeadm_types.go +@@ -259,6 +259,21 @@ type RegistryMirrorConfiguration struct { + + // CACert defines the CA cert for the registry mirror + CACert string `json:"caCert,omitempty"` ++ ++ // Mirrors defines a list of image registry mirrors. ++ // +k8s:conversion-gen=false ++ // +optional ++ Mirrors []Mirror `json:"mirrors,omitempty"` ++} ++ ++// Mirror holds the settings for mirroring a registry. ++type Mirror struct { ++ // Registry defines the registry we are mirroring to the endpoint. ++ Registry string `json:"registry,omitempty"` ++ ++ // Endpoints defines the registry mirror endpoints to use for pulling images. ++ // Currently we support only one private registry. Hence endpoints would have only one entry. ++ Endpoints []string `json:"endpoints,omitempty"` + } + + // ControlPlaneComponent holds settings common to control plane component of the cluster. +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +index c02aee696..a4cb4b3ab 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go +@@ -420,6 +420,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*Mirror)(nil), (*v1beta1.Mirror)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1alpha4_Mirror_To_v1beta1_Mirror(a.(*Mirror), b.(*v1beta1.Mirror), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.Mirror)(nil), (*Mirror)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_Mirror_To_v1alpha4_Mirror(a.(*v1beta1.Mirror), b.(*Mirror), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*NTP)(nil), (*v1beta1.NTP)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1alpha4_NTP_To_v1beta1_NTP(a.(*NTP), b.(*v1beta1.NTP), scope) + }); err != nil { +@@ -1858,6 +1868,28 @@ func Convert_v1beta1_LocalEtcd_To_v1alpha4_LocalEtcd(in *v1beta1.LocalEtcd, out + return autoConvert_v1beta1_LocalEtcd_To_v1alpha4_LocalEtcd(in, out, s) + } + ++func autoConvert_v1alpha4_Mirror_To_v1beta1_Mirror(in *Mirror, out *v1beta1.Mirror, s conversion.Scope) error { ++ out.Registry = in.Registry ++ out.Endpoints = *(*[]string)(unsafe.Pointer(&in.Endpoints)) ++ return nil ++} ++ ++// Convert_v1alpha4_Mirror_To_v1beta1_Mirror is an autogenerated conversion function. ++func Convert_v1alpha4_Mirror_To_v1beta1_Mirror(in *Mirror, out *v1beta1.Mirror, s conversion.Scope) error { ++ return autoConvert_v1alpha4_Mirror_To_v1beta1_Mirror(in, out, s) ++} ++ ++func autoConvert_v1beta1_Mirror_To_v1alpha4_Mirror(in *v1beta1.Mirror, out *Mirror, s conversion.Scope) error { ++ out.Registry = in.Registry ++ out.Endpoints = *(*[]string)(unsafe.Pointer(&in.Endpoints)) ++ return nil ++} ++ ++// Convert_v1beta1_Mirror_To_v1alpha4_Mirror is an autogenerated conversion function. ++func Convert_v1beta1_Mirror_To_v1alpha4_Mirror(in *v1beta1.Mirror, out *Mirror, s conversion.Scope) error { ++ return autoConvert_v1beta1_Mirror_To_v1alpha4_Mirror(in, out, s) ++} ++ + func autoConvert_v1alpha4_NTP_To_v1beta1_NTP(in *NTP, out *v1beta1.NTP, s conversion.Scope) error { + out.Servers = *(*[]string)(unsafe.Pointer(&in.Servers)) + out.Enabled = (*bool)(unsafe.Pointer(in.Enabled)) +@@ -2003,6 +2035,7 @@ func Convert_v1beta1_ProxyConfiguration_To_v1alpha4_ProxyConfiguration(in *v1bet + func autoConvert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { + out.Endpoint = in.Endpoint + out.CACert = in.CACert ++ // INFO: in.Mirrors opted out of conversion generation + return nil + } + +@@ -2014,6 +2047,7 @@ func Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfi + func autoConvert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { + out.Endpoint = in.Endpoint + out.CACert = in.CACert ++ // INFO: in.Mirrors opted out of conversion generation + return nil + } + +diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +index 4c3225e59..615ea1651 100644 +--- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.deepcopy.go +@@ -354,7 +354,7 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) +- out.RegistryMirror = in.RegistryMirror ++ in.RegistryMirror.DeepCopyInto(&out.RegistryMirror) + in.Etcd.DeepCopyInto(&out.Etcd) + out.Networking = in.Networking + in.APIServer.DeepCopyInto(&out.APIServer) +@@ -744,7 +744,7 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) +- out.RegistryMirror = in.RegistryMirror ++ in.RegistryMirror.DeepCopyInto(&out.RegistryMirror) + in.NodeRegistration.DeepCopyInto(&out.NodeRegistration) + in.Discovery.DeepCopyInto(&out.Discovery) + if in.ControlPlane != nil { +@@ -1097,6 +1097,26 @@ func (in *LocalEtcd) DeepCopy() *LocalEtcd { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *Mirror) DeepCopyInto(out *Mirror) { ++ *out = *in ++ if in.Endpoints != nil { ++ in, out := &in.Endpoints, &out.Endpoints ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Mirror. ++func (in *Mirror) DeepCopy() *Mirror { ++ if in == nil { ++ return nil ++ } ++ out := new(Mirror) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in MountPoints) DeepCopyInto(out *MountPoints) { + { +@@ -1254,6 +1274,13 @@ func (in *ProxyConfiguration) DeepCopy() *ProxyConfiguration { + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *RegistryMirrorConfiguration) DeepCopyInto(out *RegistryMirrorConfiguration) { + *out = *in ++ if in.Mirrors != nil { ++ in, out := &in.Mirrors, &out.Mirrors ++ *out = make([]Mirror, len(*in)) ++ for i := range *in { ++ (*in)[i].DeepCopyInto(&(*out)[i]) ++ } ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new RegistryMirrorConfiguration. +diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +index ed965709a..e3e4f3ef8 100644 +--- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go ++++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +@@ -278,6 +278,21 @@ type RegistryMirrorConfiguration struct { + + // CACert defines the CA cert for the registry mirror + CACert string `json:"caCert,omitempty"` ++ ++ // Mirrors defines a list of image registry mirrors. ++ // +k8s:conversion-gen=false ++ // +optional ++ Mirrors []Mirror `json:"mirrors,omitempty"` ++} ++ ++// Mirror holds the settings for mirroring a registry. ++type Mirror struct { ++ // Registry defines the registry we are mirroring to the endpoint. ++ Registry string `json:"registry,omitempty"` ++ ++ // Endpoints defines the registry mirror endpoints to use for pulling images. ++ // Currently we support only one private registry. Hence endpoints would have only one entry. ++ Endpoints []string `json:"endpoints,omitempty"` + } + + // ControlPlaneComponent holds settings common to control plane component of the cluster. +diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +index 9fefdcb62..7faf6f8c9 100644 +--- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +@@ -354,7 +354,7 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) +- out.RegistryMirror = in.RegistryMirror ++ in.RegistryMirror.DeepCopyInto(&out.RegistryMirror) + in.Etcd.DeepCopyInto(&out.Etcd) + out.Networking = in.Networking + in.APIServer.DeepCopyInto(&out.APIServer) +@@ -789,7 +789,7 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) +- out.RegistryMirror = in.RegistryMirror ++ in.RegistryMirror.DeepCopyInto(&out.RegistryMirror) + in.NodeRegistration.DeepCopyInto(&out.NodeRegistration) + in.Discovery.DeepCopyInto(&out.Discovery) + if in.ControlPlane != nil { +@@ -1158,6 +1158,26 @@ func (in *LocalEtcd) DeepCopy() *LocalEtcd { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *Mirror) DeepCopyInto(out *Mirror) { ++ *out = *in ++ if in.Endpoints != nil { ++ in, out := &in.Endpoints, &out.Endpoints ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Mirror. ++func (in *Mirror) DeepCopy() *Mirror { ++ if in == nil { ++ return nil ++ } ++ out := new(Mirror) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in MountPoints) DeepCopyInto(out *MountPoints) { + { +@@ -1346,6 +1366,13 @@ func (in *ProxyConfiguration) DeepCopy() *ProxyConfiguration { + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *RegistryMirrorConfiguration) DeepCopyInto(out *RegistryMirrorConfiguration) { + *out = *in ++ if in.Mirrors != nil { ++ in, out := &in.Mirrors, &out.Mirrors ++ *out = make([]Mirror, len(*in)) ++ for i := range *in { ++ (*in)[i].DeepCopyInto(&(*out)[i]) ++ } ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new RegistryMirrorConfiguration. +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +index 3b4cbbf3f..4a8934c6e 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml +@@ -538,6 +538,25 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry mirrors. ++ items: ++ description: Mirror holds the settings for mirroring a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror endpoints ++ to use for pulling images. Currently we support only ++ one private registry. Hence endpoints would have only ++ one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are mirroring ++ to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + scheduler: + description: Scheduler contains extra settings for the scheduler +@@ -1296,6 +1315,25 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry mirrors. ++ items: ++ description: Mirror holds the settings for mirroring a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror endpoints ++ to use for pulling images. Currently we support only ++ one private registry. Hence endpoints would have only ++ one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are mirroring ++ to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + type: object + mounts: +@@ -1996,6 +2034,25 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry mirrors. ++ items: ++ description: Mirror holds the settings for mirroring a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror endpoints ++ to use for pulling images. Currently we support only ++ one private registry. Hence endpoints would have only ++ one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are mirroring ++ to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + scheduler: + description: Scheduler contains extra settings for the scheduler +@@ -2754,6 +2811,25 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry mirrors. ++ items: ++ description: Mirror holds the settings for mirroring a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror endpoints ++ to use for pulling images. Currently we support only ++ one private registry. Hence endpoints would have only ++ one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are mirroring ++ to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + type: object + mounts: +@@ -3457,6 +3533,25 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry mirrors. ++ items: ++ description: Mirror holds the settings for mirroring a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror endpoints ++ to use for pulling images. Currently we support only ++ one private registry. Hence endpoints would have only ++ one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are mirroring ++ to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + scheduler: + description: Scheduler contains extra settings for the scheduler +@@ -4310,6 +4405,25 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry mirrors. ++ items: ++ description: Mirror holds the settings for mirroring a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror endpoints ++ to use for pulling images. Currently we support only ++ one private registry. Hence endpoints would have only ++ one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are mirroring ++ to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + skipPhases: + description: SkipPhases is a list of phases to skip during command +diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +index e25795947..235a375d2 100644 +--- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml ++++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml +@@ -573,6 +573,27 @@ spec: + description: Endpoint defines the registry mirror + endpoint to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry ++ mirror endpoints to use for pulling images. ++ Currently we support only one private registry. ++ Hence endpoints would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we ++ are mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + scheduler: + description: Scheduler contains extra settings for the +@@ -1377,6 +1398,27 @@ spec: + description: Endpoint defines the registry mirror + endpoint to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry ++ mirror endpoints to use for pulling images. ++ Currently we support only one private registry. ++ Hence endpoints would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we ++ are mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + type: object + mounts: +@@ -2048,6 +2090,27 @@ spec: + description: Endpoint defines the registry mirror + endpoint to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry ++ mirror endpoints to use for pulling images. ++ Currently we support only one private registry. ++ Hence endpoints would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we ++ are mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + scheduler: + description: Scheduler contains extra settings for the +@@ -2854,6 +2917,27 @@ spec: + description: Endpoint defines the registry mirror + endpoint to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry ++ mirror endpoints to use for pulling images. ++ Currently we support only one private registry. ++ Hence endpoints would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we ++ are mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + type: object + mounts: +@@ -3553,6 +3637,27 @@ spec: + description: Endpoint defines the registry mirror + endpoint to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry ++ mirror endpoints to use for pulling images. ++ Currently we support only one private registry. ++ Hence endpoints would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we ++ are mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + scheduler: + description: Scheduler contains extra settings for the +@@ -4465,6 +4570,27 @@ spec: + description: Endpoint defines the registry mirror + endpoint to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry ++ mirror endpoints to use for pulling images. ++ Currently we support only one private registry. ++ Hence endpoints would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we ++ are mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + skipPhases: + description: SkipPhases is a list of phases to skip during +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +index df222b943..f378c3362 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go +@@ -74,8 +74,11 @@ no-proxy = [{{stringsJoin .NoProxyEndpoints "," }}] + {{- end -}} + ` + registryMirrorTemplate = `{{ define "registryMirrorSettings" -}} +-[settings.container-registry.mirrors] +-"public.ecr.aws" = ["https://{{.RegistryMirrorEndpoint}}"] ++{{- range $orig, $mirror := .RegistryMirrorMap }} ++[[settings.container-registry.mirrors]] ++registry = "{{ $orig }}" ++endpoint = [{{stringsJoin $mirror "," }}] ++{{- end -}} + {{- end -}} + ` + registryMirrorCACertTemplate = `{{ define "registryMirrorCACertSettings" -}} +@@ -88,16 +91,21 @@ trusted=true + // to "public.ecr.aws" rather than the mirror's endpoint + // TODO: Once the bottlerocket fixes are in we need to remove the "public.ecr.aws" creds + registryMirrorCredentialsTemplate = `{{define "registryMirrorCredentialsSettings" -}} ++{{- range $orig, $mirror := .RegistryMirrorMap }} ++{{- if (eq $orig "public.ecr.aws")}} + [[settings.container-registry.credentials]] +-registry = "public.ecr.aws" +-username = "{{.RegistryMirrorUsername}}" +-password = "{{.RegistryMirrorPassword}}" ++registry = "{{ $orig }}" ++username = "{{$.RegistryMirrorUsername}}" ++password = "{{$.RegistryMirrorPassword}}" ++{{- end }} ++{{- end }} + [[settings.container-registry.credentials]] + registry = "{{.RegistryMirrorEndpoint}}" + username = "{{.RegistryMirrorUsername}}" + password = "{{.RegistryMirrorPassword}}" + {{- end -}} + ` ++ + nodeLabelsTemplate = `{{ define "nodeLabelSettings" -}} + [settings.kubernetes.node-labels] + {{.NodeLabels}} +@@ -153,7 +161,7 @@ trusted = true + {{- end -}} + + +-{{- if (ne .RegistryMirrorEndpoint "")}} ++{{- if .RegistryMirrorMap}} + {{template "registryMirrorSettings" .}} + {{- end -}} + +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +index 2ee2d942b..ed58dc035 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go +@@ -134,8 +134,10 @@ provider-id = "PROVIDERID" + + [settings.network] + hostname = "hostname" +-[settings.container-registry.mirrors] +-"public.ecr.aws" = ["https://REGISTRY_ENDPOINT"] ++ ++[[settings.container-registry.mirrors]] ++registry = "public.ecr.aws" ++endpoint = ["REGISTRY_ENDPOINT"] + [settings.pki.registry-mirror-ca] + data = "UkVHSVNUUllfQ0E=" + trusted=true` +@@ -162,11 +164,14 @@ provider-id = "PROVIDERID" + + [settings.network] + hostname = "hostname" +-[settings.container-registry.mirrors] +-"public.ecr.aws" = ["https://REGISTRY_ENDPOINT"] ++ ++[[settings.container-registry.mirrors]] ++registry = "public.ecr.aws" ++endpoint = ["REGISTRY_ENDPOINT"] + [settings.pki.registry-mirror-ca] + data = "UkVHSVNUUllfQ0E=" + trusted=true ++ + [[settings.container-registry.credentials]] + registry = "public.ecr.aws" + username = "admin" +@@ -340,6 +345,39 @@ trusted = true + [settings.pki.bundle2] + data = "MTIzNDU2" + trusted = true` ++ ++ registryMirrorMultipleMirrorsUserData = ` ++[settings.host-containers.admin] ++enabled = true ++superpowered = true ++source = "ADMIN_REPO:ADMIN_TAG" ++user-data = "CnsKCSJzc2giOiB7CgkJImF1dGhvcml6ZWQta2V5cyI6IFsic3NoLXJzYSBBQUEuLi4iXQoJfQp9" ++[settings.host-containers.kubeadm-bootstrap] ++enabled = true ++superpowered = true ++source = "BOOTSTRAP_REPO:BOOTSTRAP_TAG" ++user-data = "Qk9UVExFUk9DS0VUX0JPT1RTVFJBUF9VU0VSREFUQQ==" ++ ++[settings.kubernetes] ++cluster-domain = "cluster.local" ++standalone-mode = true ++authentication-mode = "tls" ++server-tls-bootstrap = false ++pod-infra-container-image = "PAUSE_REPO:PAUSE_TAG" ++provider-id = "PROVIDERID" ++ ++[settings.network] ++hostname = "hostname" ++ ++[[settings.container-registry.mirrors]] ++registry = "docker.io" ++endpoint = ["REGISTRY_ENDPOINT"] ++[[settings.container-registry.mirrors]] ++registry = "public.ecr.aws" ++endpoint = ["REGISTRY_ENDPOINT"] ++[settings.pki.registry-mirror-ca] ++data = "UkVHSVNUUllfQ0E=" ++trusted=true` + ) + + var ( +@@ -622,6 +660,32 @@ func TestGetBottlerocketNodeUserData(t *testing.T) { + }, + output: userDataWithCertBundle, + }, ++ { ++ name: "with multiple registries to mirror", ++ config: &BottlerocketConfig{ ++ BottlerocketAdmin: brAdmin, ++ BottlerocketBootstrap: brBootstrap, ++ Hostname: hostname, ++ Pause: pause, ++ KubeletExtraArgs: map[string]string{ ++ "provider-id": "PROVIDERID", ++ }, ++ RegistryMirrorConfiguration: bootstrapv1.RegistryMirrorConfiguration{ ++ CACert: "REGISTRY_CA", ++ Mirrors: []bootstrapv1.Mirror{ ++ { ++ Registry: "docker.io", ++ Endpoints: []string{"REGISTRY_ENDPOINT"}, ++ }, ++ { ++ Registry: "public.ecr.aws", ++ Endpoints: []string{"REGISTRY_ENDPOINT"}, ++ }, ++ }, ++ }, ++ }, ++ output: registryMirrorMultipleMirrorsUserData, ++ }, + } + for _, testcase := range testcases { + t.Run(testcase.name, func(t *testing.T) { +diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +index ce796f206..f596d7b01 100644 +--- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go ++++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go +@@ -4,6 +4,7 @@ import ( + "bytes" + "encoding/base64" + "fmt" ++ "regexp" + "strconv" + "strings" + "text/template" +@@ -63,6 +64,7 @@ type BottlerocketSettingsInput struct { + BootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer + SysctlSettings string + CertBundles []bootstrapv1.CertBundle ++ RegistryMirrorMap map[string][]string + } + + // HostPath holds the path and type of a host path volume. +@@ -227,15 +229,14 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot + } + + bottlerocketInput := &BottlerocketSettingsInput{ +- PauseContainerSource: fmt.Sprintf("%s:%s", config.Pause.ImageRepository, config.Pause.ImageTag), +- HTTPSProxyEndpoint: config.ProxyConfiguration.HTTPSProxy, +- RegistryMirrorEndpoint: config.RegistryMirrorConfiguration.Endpoint, +- NodeLabels: parseNodeLabels(config.KubeletExtraArgs["node-labels"]), // empty string if it does not exist +- Taints: parseTaints(config.Taints), // empty string if it does not exist +- ProviderID: config.KubeletExtraArgs["provider-id"], +- Hostname: config.Hostname, +- HostContainers: hostContainers, +- BootstrapContainers: config.BottlerocketCustomBootstrapContainers, ++ PauseContainerSource: fmt.Sprintf("%s:%s", config.Pause.ImageRepository, config.Pause.ImageTag), ++ HTTPSProxyEndpoint: config.ProxyConfiguration.HTTPSProxy, ++ NodeLabels: parseNodeLabels(config.KubeletExtraArgs["node-labels"]), // empty string if it does not exist ++ Taints: parseTaints(config.Taints), // empty string if it does not exist ++ ProviderID: config.KubeletExtraArgs["provider-id"], ++ Hostname: config.Hostname, ++ HostContainers: hostContainers, ++ BootstrapContainers: config.BottlerocketCustomBootstrapContainers, + } + + if len(config.ProxyConfiguration.NoProxy) > 0 { +@@ -243,6 +244,31 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot + bottlerocketInput.NoProxyEndpoints = append(bottlerocketInput.NoProxyEndpoints, strconv.Quote(noProxy)) + } + } ++ ++ // When RegistryMirrorConfiguration.Endpoint is specified, we default the mirror to public.ecr.aws. ++ // This was done for backward compatability, since public.ecr.aws was the only supported registry before. ++ // For existing customers this ensures that their nodes dont rollout, unless more mirrors are specified explicitly. ++ // If RegistryMirrorConfiguration.Endpoint is not specified, we iterate the RegistryMirrorConfiguration.Mirrors to setup the mirrors. ++ bottlerocketInput.RegistryMirrorMap = make(map[string][]string) ++ endpointRegex := regexp.MustCompile(`^(https?:\/\/)?[\w\.\:\-]+`) ++ if config.RegistryMirrorConfiguration.Endpoint != "" { ++ bottlerocketInput.RegistryMirrorMap["public.ecr.aws"] = []string{strconv.Quote(config.RegistryMirrorConfiguration.Endpoint)} ++ if endpoint := endpointRegex.FindStringSubmatch(config.RegistryMirrorConfiguration.Endpoint); endpoint != nil { ++ bottlerocketInput.RegistryMirrorEndpoint = endpoint[0] ++ } ++ } else if len(config.RegistryMirrorConfiguration.Mirrors) > 0 { ++ for _, mirror := range config.RegistryMirrorConfiguration.Mirrors { ++ for _, endpoint := range mirror.Endpoints { ++ bottlerocketInput.RegistryMirrorMap[mirror.Registry] = append(bottlerocketInput.RegistryMirrorMap[mirror.Registry], strconv.Quote(endpoint)) ++ } ++ } ++ ++ // Right now we support only one private registry. Hence defaulting to first entry. ++ if endpoint := endpointRegex.FindStringSubmatch(config.RegistryMirrorConfiguration.Mirrors[0].Endpoints[0]); endpoint != nil { ++ bottlerocketInput.RegistryMirrorEndpoint = endpoint[0] ++ } ++ } ++ + if config.RegistryMirrorConfiguration.CACert != "" { + bottlerocketInput.RegistryMirrorCACert = base64.StdEncoding.EncodeToString([]byte(config.RegistryMirrorConfiguration.CACert)) + } +diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go +index 4e8b7c5e0..4d3d251d6 100644 +--- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go ++++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go +@@ -490,7 +490,9 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex + if scope.Config.Spec.ClusterConfiguration.Proxy.HTTPSProxy != "" { + bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.ClusterConfiguration.Proxy + } +- if scope.Config.Spec.ClusterConfiguration.RegistryMirror.Endpoint != "" { ++ ++ if scope.Config.Spec.ClusterConfiguration.RegistryMirror.Endpoint != "" || ++ len(scope.Config.Spec.ClusterConfiguration.RegistryMirror.Mirrors) != 0 { + bottlerocketConfig.RegistryMirrorConfiguration = scope.Config.Spec.ClusterConfiguration.RegistryMirror + registryUsername, registryPassword, err := r.resolveRegistryCredentials(ctx, scope.Config) + if err != nil { +@@ -718,7 +720,9 @@ func (r *KubeadmConfigReconciler) joinWorker(ctx context.Context, scope *Scope) + if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { + bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy + } +- if scope.Config.Spec.JoinConfiguration.RegistryMirror.Endpoint != "" { ++ ++ if scope.Config.Spec.JoinConfiguration.RegistryMirror.Endpoint != "" || ++ len(scope.Config.Spec.JoinConfiguration.RegistryMirror.Mirrors) != 0 { + bottlerocketConfig.RegistryMirrorConfiguration = scope.Config.Spec.JoinConfiguration.RegistryMirror + registryUsername, registryPassword, err := r.resolveRegistryCredentials(ctx, scope.Config) + if err != nil { +@@ -868,7 +872,9 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S + if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { + bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy + } +- if scope.Config.Spec.ClusterConfiguration.RegistryMirror.Endpoint != "" { ++ ++ if scope.Config.Spec.ClusterConfiguration.RegistryMirror.Endpoint != "" || ++ len(scope.Config.Spec.ClusterConfiguration.RegistryMirror.Mirrors) != 0 { + bottlerocketConfig.RegistryMirrorConfiguration = scope.Config.Spec.ClusterConfiguration.RegistryMirror + registryUsername, registryPassword, err := r.resolveRegistryCredentials(ctx, scope.Config) + if err != nil { +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/types.go b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +index be0b0725c..8ae11ae0d 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/types.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/types.go +@@ -257,6 +257,21 @@ type RegistryMirrorConfiguration struct { + + // CACert defines the CA cert for the registry mirror + CACert string `json:"caCert,omitempty"` ++ ++ // Mirrors defines a list of image registry mirrors. ++ // +k8s:conversion-gen=false ++ // +optional ++ Mirrors []Mirror `json:"mirrors,omitempty"` ++} ++ ++// Mirror holds the settings for mirroring a registry. ++type Mirror struct { ++ // Registry defines the registry we are mirroring to the endpoint. ++ Registry string `json:"registry,omitempty"` ++ ++ // Endpoints defines the registry mirror endpoints to use for pulling images. ++ // Currently we support only one private registry. Hence endpoints would have only one entry. ++ Endpoints []string `json:"endpoints,omitempty"` + } + + // ControlPlaneComponent holds settings common to control plane component of the cluster. +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go +index f77e22f31..3e1aa5b5c 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.conversion.go +@@ -308,6 +308,16 @@ func RegisterConversions(s *runtime.Scheme) error { + }); err != nil { + return err + } ++ if err := s.AddGeneratedConversionFunc((*Mirror)(nil), (*v1beta1.Mirror)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_upstreamv1beta1_Mirror_To_v1beta1_Mirror(a.(*Mirror), b.(*v1beta1.Mirror), scope) ++ }); err != nil { ++ return err ++ } ++ if err := s.AddGeneratedConversionFunc((*v1beta1.Mirror)(nil), (*Mirror)(nil), func(a, b interface{}, scope conversion.Scope) error { ++ return Convert_v1beta1_Mirror_To_upstreamv1beta1_Mirror(a.(*v1beta1.Mirror), b.(*Mirror), scope) ++ }); err != nil { ++ return err ++ } + if err := s.AddGeneratedConversionFunc((*Networking)(nil), (*v1beta1.Networking)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_upstreamv1beta1_Networking_To_v1beta1_Networking(a.(*Networking), b.(*v1beta1.Networking), scope) + }); err != nil { +@@ -1225,6 +1235,28 @@ func Convert_v1beta1_LocalEtcd_To_upstreamv1beta1_LocalEtcd(in *v1beta1.LocalEtc + return autoConvert_v1beta1_LocalEtcd_To_upstreamv1beta1_LocalEtcd(in, out, s) + } + ++func autoConvert_upstreamv1beta1_Mirror_To_v1beta1_Mirror(in *Mirror, out *v1beta1.Mirror, s conversion.Scope) error { ++ out.Registry = in.Registry ++ out.Endpoints = *(*[]string)(unsafe.Pointer(&in.Endpoints)) ++ return nil ++} ++ ++// Convert_upstreamv1beta1_Mirror_To_v1beta1_Mirror is an autogenerated conversion function. ++func Convert_upstreamv1beta1_Mirror_To_v1beta1_Mirror(in *Mirror, out *v1beta1.Mirror, s conversion.Scope) error { ++ return autoConvert_upstreamv1beta1_Mirror_To_v1beta1_Mirror(in, out, s) ++} ++ ++func autoConvert_v1beta1_Mirror_To_upstreamv1beta1_Mirror(in *v1beta1.Mirror, out *Mirror, s conversion.Scope) error { ++ out.Registry = in.Registry ++ out.Endpoints = *(*[]string)(unsafe.Pointer(&in.Endpoints)) ++ return nil ++} ++ ++// Convert_v1beta1_Mirror_To_upstreamv1beta1_Mirror is an autogenerated conversion function. ++func Convert_v1beta1_Mirror_To_upstreamv1beta1_Mirror(in *v1beta1.Mirror, out *Mirror, s conversion.Scope) error { ++ return autoConvert_v1beta1_Mirror_To_upstreamv1beta1_Mirror(in, out, s) ++} ++ + func autoConvert_upstreamv1beta1_Networking_To_v1beta1_Networking(in *Networking, out *v1beta1.Networking, s conversion.Scope) error { + out.ServiceSubnet = in.ServiceSubnet + out.PodSubnet = in.PodSubnet +@@ -1321,6 +1353,7 @@ func Convert_v1beta1_ProxyConfiguration_To_upstreamv1beta1_ProxyConfiguration(in + func autoConvert_upstreamv1beta1_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfiguration(in *RegistryMirrorConfiguration, out *v1beta1.RegistryMirrorConfiguration, s conversion.Scope) error { + out.Endpoint = in.Endpoint + out.CACert = in.CACert ++ // INFO: in.Mirrors opted out of conversion generation + return nil + } + +@@ -1332,6 +1365,7 @@ func Convert_upstreamv1beta1_RegistryMirrorConfiguration_To_v1beta1_RegistryMirr + func autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta1_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { + out.Endpoint = in.Endpoint + out.CACert = in.CACert ++ // INFO: in.Mirrors opted out of conversion generation + return nil + } + +diff --git a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +index ef10cb0b3..b8ef3ee30 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta1/zz_generated.deepcopy.go +@@ -353,7 +353,7 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { + out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) +- out.RegistryMirror = in.RegistryMirror ++ in.RegistryMirror.DeepCopyInto(&out.RegistryMirror) + in.Etcd.DeepCopyInto(&out.Etcd) + out.Networking = in.Networking + in.APIServer.DeepCopyInto(&out.APIServer) +@@ -643,7 +643,7 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { + out.BottlerocketAdmin = in.BottlerocketAdmin + out.BottlerocketControl = in.BottlerocketControl + in.Proxy.DeepCopyInto(&out.Proxy) +- out.RegistryMirror = in.RegistryMirror ++ in.RegistryMirror.DeepCopyInto(&out.RegistryMirror) + in.NodeRegistration.DeepCopyInto(&out.NodeRegistration) + in.Discovery.DeepCopyInto(&out.Discovery) + if in.ControlPlane != nil { +@@ -740,6 +740,26 @@ func (in *LocalEtcd) DeepCopy() *LocalEtcd { + return out + } + ++// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. ++func (in *Mirror) DeepCopyInto(out *Mirror) { ++ *out = *in ++ if in.Endpoints != nil { ++ in, out := &in.Endpoints, &out.Endpoints ++ *out = make([]string, len(*in)) ++ copy(*out, *in) ++ } ++} ++ ++// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Mirror. ++func (in *Mirror) DeepCopy() *Mirror { ++ if in == nil { ++ return nil ++ } ++ out := new(Mirror) ++ in.DeepCopyInto(out) ++ return out ++} ++ + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *Networking) DeepCopyInto(out *Networking) { + *out = *in +@@ -823,6 +843,13 @@ func (in *ProxyConfiguration) DeepCopy() *ProxyConfiguration { + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. + func (in *RegistryMirrorConfiguration) DeepCopyInto(out *RegistryMirrorConfiguration) { + *out = *in ++ if in.Mirrors != nil { ++ in, out := &in.Mirrors, &out.Mirrors ++ *out = make([]Mirror, len(*in)) ++ for i := range *in { ++ (*in)[i].DeepCopyInto(&(*out)[i]) ++ } ++ } + } + + // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new RegistryMirrorConfiguration. +diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go +index 3b12557c4..2f462fbe6 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go +@@ -1042,6 +1042,7 @@ func Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirr + func autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { + out.Endpoint = in.Endpoint + out.CACert = in.CACert ++ // INFO: in.Mirrors opted out of conversion generation + return nil + } + +diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go +index 6d812f516..dfff19e2d 100644 +--- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go ++++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go +@@ -1055,6 +1055,7 @@ func Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirr + func autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { + out.Endpoint = in.Endpoint + out.CACert = in.CACert ++ // INFO: in.Mirrors opted out of conversion generation + return nil + } + +diff --git a/config/crd/bases/cluster.x-k8s.io_machinedeployments.yaml b/config/crd/bases/cluster.x-k8s.io_machinedeployments.yaml +index 98c907371..2062fe6ff 100644 +--- a/config/crd/bases/cluster.x-k8s.io_machinedeployments.yaml ++++ b/config/crd/bases/cluster.x-k8s.io_machinedeployments.yaml +@@ -703,7 +703,6 @@ spec: + enum: + - RollingUpdate + - OnDelete +- - InPlace + type: string + type: object + template: +@@ -1197,6 +1196,7 @@ spec: + enum: + - RollingUpdate + - OnDelete ++ - InPlace + type: string + type: object + template: +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +index fc1332eef..9cca28afb 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml +@@ -630,6 +630,27 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror ++ endpoints to use for pulling images. Currently ++ we support only one private registry. Hence endpoints ++ would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are ++ mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + scheduler: + description: Scheduler contains extra settings for the scheduler +@@ -1418,6 +1439,27 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror ++ endpoints to use for pulling images. Currently ++ we support only one private registry. Hence endpoints ++ would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are ++ mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + type: object + mounts: +@@ -2255,6 +2297,27 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror ++ endpoints to use for pulling images. Currently ++ we support only one private registry. Hence endpoints ++ would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are ++ mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + scheduler: + description: Scheduler contains extra settings for the scheduler +@@ -3045,6 +3108,27 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror ++ endpoints to use for pulling images. Currently ++ we support only one private registry. Hence endpoints ++ would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are ++ mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + type: object + mounts: +@@ -3971,6 +4055,27 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror ++ endpoints to use for pulling images. Currently ++ we support only one private registry. Hence endpoints ++ would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are ++ mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + scheduler: + description: Scheduler contains extra settings for the scheduler +@@ -4862,6 +4967,27 @@ spec: + description: Endpoint defines the registry mirror endpoint + to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry mirror ++ endpoints to use for pulling images. Currently ++ we support only one private registry. Hence endpoints ++ would have only one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry we are ++ mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + skipPhases: + description: SkipPhases is a list of phases to skip during +diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +index ee4180f67..44712fe7a 100644 +--- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml ++++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml +@@ -605,6 +605,28 @@ spec: + description: Endpoint defines the registry mirror + endpoint to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry ++ mirror endpoints to use for pulling images. ++ Currently we support only one private ++ registry. Hence endpoints would have only ++ one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry ++ we are mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + scheduler: + description: Scheduler contains extra settings for +@@ -1447,6 +1469,28 @@ spec: + description: Endpoint defines the registry mirror + endpoint to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry ++ mirror endpoints to use for pulling images. ++ Currently we support only one private ++ registry. Hence endpoints would have only ++ one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry ++ we are mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + type: object + mounts: +@@ -2315,6 +2359,28 @@ spec: + description: Endpoint defines the registry mirror + endpoint to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry ++ mirror endpoints to use for pulling images. ++ Currently we support only one private ++ registry. Hence endpoints would have only ++ one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry ++ we are mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + scheduler: + description: Scheduler contains extra settings for +@@ -3267,6 +3333,28 @@ spec: + description: Endpoint defines the registry mirror + endpoint to use for pulling images + type: string ++ mirrors: ++ description: Mirrors defines a list of image registry ++ mirrors. ++ items: ++ description: Mirror holds the settings for mirroring ++ a registry. ++ properties: ++ endpoints: ++ description: Endpoints defines the registry ++ mirror endpoints to use for pulling images. ++ Currently we support only one private ++ registry. Hence endpoints would have only ++ one entry. ++ items: ++ type: string ++ type: array ++ registry: ++ description: Registry defines the registry ++ we are mirroring to the endpoint. ++ type: string ++ type: object ++ type: array + type: object + skipPhases: + description: SkipPhases is a list of phases to skip +-- +2.42.0 + diff --git a/projects/kubernetes-sigs/cluster-api/patches/0040-Fix-MD-controller-reconcilation-with-in-place.patch b/projects/kubernetes-sigs/cluster-api/patches/0038-Fix-MD-controller-reconcilation-with-in-place.patch similarity index 99% rename from projects/kubernetes-sigs/cluster-api/patches/0040-Fix-MD-controller-reconcilation-with-in-place.patch rename to projects/kubernetes-sigs/cluster-api/patches/0038-Fix-MD-controller-reconcilation-with-in-place.patch index d1b091de1e..e4a5de89c2 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0040-Fix-MD-controller-reconcilation-with-in-place.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0038-Fix-MD-controller-reconcilation-with-in-place.patch @@ -1,7 +1,7 @@ -From 7c03af1b3077e9b633c42d4ea13fc3ed9d41324d Mon Sep 17 00:00:00 2001 +From 25dc95a348a5921ae6d2b9eb9f6e59cdfd5ae012 Mon Sep 17 00:00:00 2001 From: Abhinav Pandey Date: Mon, 5 Feb 2024 23:45:36 -0800 -Subject: [PATCH 39/40] Fix MD controller reconcilation with in-place +Subject: [PATCH 38/40] Fix MD controller reconcilation with in-place --- .../machinedeployment_controller_test.go | 398 ++++++++++++++++++ @@ -662,5 +662,5 @@ index 203cd90f8..0f4bb48f3 100644 return 0, fmt.Errorf("failed to compute replicas: deployment strategy %v isn't supported", deployment.Spec.Strategy.Type) } -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0039-Adding-support-for-multiple-registry-mirrors-in-bott.patch b/projects/kubernetes-sigs/cluster-api/patches/0039-Adding-support-for-multiple-registry-mirrors-in-bott.patch deleted file mode 100644 index 743c7ed5a8..0000000000 --- a/projects/kubernetes-sigs/cluster-api/patches/0039-Adding-support-for-multiple-registry-mirrors-in-bott.patch +++ /dev/null @@ -1,660 +0,0 @@ -From bfe02ef55483c5cb0bdbb77877550a42695acbcd Mon Sep 17 00:00:00 2001 -From: Aravind Ramalingam -Date: Mon, 22 Jan 2024 12:47:26 -0800 -Subject: [PATCH] Adding support for multiple registry mirrors in bottlerocket - ---- - .../api/v1alpha4/zz_generated.conversion.go | 1 + - .../kubeadm/api/v1beta1/kubeadm_types.go | 15 ++++ - .../api/v1beta1/zz_generated.deepcopy.go | 34 ++++++++- - ...strap.cluster.x-k8s.io_kubeadmconfigs.yaml | 38 ++++++++++ - ...uster.x-k8s.io_kubeadmconfigtemplates.yaml | 42 +++++++++++ - .../internal/bottlerocket/bootstrap.go | 20 ++++-- - .../internal/bottlerocket/bootstrap_test.go | 72 +++++++++++++++++-- - .../internal/bottlerocket/bottlerocket.go | 44 +++++++++--- - .../controllers/kubeadmconfig_controller.go | 12 +++- - .../zz_generated.conversion.go | 1 + - .../zz_generated.conversion.go | 1 + - ...cluster.x-k8s.io_kubeadmcontrolplanes.yaml | 42 +++++++++++ - ...x-k8s.io_kubeadmcontrolplanetemplates.yaml | 44 ++++++++++++ - .../test/builder/zz_generated.deepcopy.go | 23 ++++++ - 14 files changed, 364 insertions(+), 25 deletions(-) - -diff --git a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -index d43c45841..6f0447507 100644 ---- a/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/api/v1alpha4/zz_generated.conversion.go -@@ -1720,6 +1720,7 @@ func Convert_v1alpha4_RegistryMirrorConfiguration_To_v1beta1_RegistryMirrorConfi - func autoConvert_v1beta1_RegistryMirrorConfiguration_To_v1alpha4_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { - out.Endpoint = in.Endpoint - out.CACert = in.CACert -+ // INFO: in.Mirrors opted out of conversion generation - return nil - } - -diff --git a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -index ed965709a..e3e4f3ef8 100644 ---- a/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -+++ b/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go -@@ -278,6 +278,21 @@ type RegistryMirrorConfiguration struct { - - // CACert defines the CA cert for the registry mirror - CACert string `json:"caCert,omitempty"` -+ -+ // Mirrors defines a list of image registry mirrors. -+ // +k8s:conversion-gen=false -+ // +optional -+ Mirrors []Mirror `json:"mirrors,omitempty"` -+} -+ -+// Mirror holds the settings for mirroring a registry. -+type Mirror struct { -+ // Registry defines the registry we are mirroring to the endpoint. -+ Registry string `json:"registry,omitempty"` -+ -+ // Endpoints defines the registry mirror endpoints to use for pulling images. -+ // Currently we support only one private registry. Hence endpoints would have only one entry. -+ Endpoints []string `json:"endpoints,omitempty"` - } - - // ControlPlaneComponent holds settings common to control plane component of the cluster. -diff --git a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -index af85cfd21..7faf6f8c9 100644 ---- a/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -+++ b/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go -@@ -353,7 +354,7 @@ func (in *ClusterConfiguration) DeepCopyInto(out *ClusterConfiguration) { - out.BottlerocketAdmin = in.BottlerocketAdmin - out.BottlerocketControl = in.BottlerocketControl - in.Proxy.DeepCopyInto(&out.Proxy) -- out.RegistryMirror = in.RegistryMirror -+ in.RegistryMirror.DeepCopyInto(&out.RegistryMirror) - in.Etcd.DeepCopyInto(&out.Etcd) - out.Networking = in.Networking - in.APIServer.DeepCopyInto(&out.APIServer) -@@ -788,7 +789,7 @@ func (in *JoinConfiguration) DeepCopyInto(out *JoinConfiguration) { - out.BottlerocketAdmin = in.BottlerocketAdmin - out.BottlerocketControl = in.BottlerocketControl - in.Proxy.DeepCopyInto(&out.Proxy) -- out.RegistryMirror = in.RegistryMirror -+ in.RegistryMirror.DeepCopyInto(&out.RegistryMirror) - in.NodeRegistration.DeepCopyInto(&out.NodeRegistration) - in.Discovery.DeepCopyInto(&out.Discovery) - if in.ControlPlane != nil { -@@ -1157,6 +1158,26 @@ func (in *LocalEtcd) DeepCopy() *LocalEtcd { - return out - } - -+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -+func (in *Mirror) DeepCopyInto(out *Mirror) { -+ *out = *in -+ if in.Endpoints != nil { -+ in, out := &in.Endpoints, &out.Endpoints -+ *out = make([]string, len(*in)) -+ copy(*out, *in) -+ } -+} -+ -+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Mirror. -+func (in *Mirror) DeepCopy() *Mirror { -+ if in == nil { -+ return nil -+ } -+ out := new(Mirror) -+ in.DeepCopyInto(out) -+ return out -+} -+ - // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. - func (in MountPoints) DeepCopyInto(out *MountPoints) { - { -@@ -1345,6 +1366,13 @@ func (in *ProxyConfiguration) DeepCopy() *ProxyConfiguration { - // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. - func (in *RegistryMirrorConfiguration) DeepCopyInto(out *RegistryMirrorConfiguration) { - *out = *in -+ if in.Mirrors != nil { -+ in, out := &in.Mirrors, &out.Mirrors -+ *out = make([]Mirror, len(*in)) -+ for i := range *in { -+ (*in)[i].DeepCopyInto(&(*out)[i]) -+ } -+ } - } - - // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new RegistryMirrorConfiguration. -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -index 9135db4f9..889745026 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigs.yaml -@@ -1675,6 +1675,25 @@ spec: - description: Endpoint defines the registry mirror endpoint - to use for pulling images - type: string -+ mirrors: -+ description: Mirrors defines a list of image registry mirrors. -+ items: -+ description: Mirror holds the settings for mirroring a registry. -+ properties: -+ endpoints: -+ description: Endpoints defines the registry mirror endpoints -+ to use for pulling images. Currently we support only -+ one private registry. Hence endpoints would have only -+ one entry. -+ items: -+ type: string -+ type: array -+ registry: -+ description: Registry defines the registry we are mirroring -+ to the endpoint. -+ type: string -+ type: object -+ type: array - type: object - scheduler: - description: Scheduler contains extra settings for the scheduler -@@ -2528,6 +2547,25 @@ spec: - description: Endpoint defines the registry mirror endpoint - to use for pulling images - type: string -+ mirrors: -+ description: Mirrors defines a list of image registry mirrors. -+ items: -+ description: Mirror holds the settings for mirroring a registry. -+ properties: -+ endpoints: -+ description: Endpoints defines the registry mirror endpoints -+ to use for pulling images. Currently we support only -+ one private registry. Hence endpoints would have only -+ one entry. -+ items: -+ type: string -+ type: array -+ registry: -+ description: Registry defines the registry we are mirroring -+ to the endpoint. -+ type: string -+ type: object -+ type: array - type: object - skipPhases: - description: SkipPhases is a list of phases to skip during command -diff --git a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -index b097f1975..b9e0d00a1 100644 ---- a/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -+++ b/bootstrap/kubeadm/config/crd/bases/bootstrap.cluster.x-k8s.io_kubeadmconfigtemplates.yaml -@@ -1737,6 +1737,27 @@ spec: - description: Endpoint defines the registry mirror - endpoint to use for pulling images - type: string -+ mirrors: -+ description: Mirrors defines a list of image registry -+ mirrors. -+ items: -+ description: Mirror holds the settings for mirroring -+ a registry. -+ properties: -+ endpoints: -+ description: Endpoints defines the registry -+ mirror endpoints to use for pulling images. -+ Currently we support only one private registry. -+ Hence endpoints would have only one entry. -+ items: -+ type: string -+ type: array -+ registry: -+ description: Registry defines the registry we -+ are mirroring to the endpoint. -+ type: string -+ type: object -+ type: array - type: object - scheduler: - description: Scheduler contains extra settings for the -@@ -2649,6 +2670,27 @@ spec: - description: Endpoint defines the registry mirror - endpoint to use for pulling images - type: string -+ mirrors: -+ description: Mirrors defines a list of image registry -+ mirrors. -+ items: -+ description: Mirror holds the settings for mirroring -+ a registry. -+ properties: -+ endpoints: -+ description: Endpoints defines the registry -+ mirror endpoints to use for pulling images. -+ Currently we support only one private registry. -+ Hence endpoints would have only one entry. -+ items: -+ type: string -+ type: array -+ registry: -+ description: Registry defines the registry we -+ are mirroring to the endpoint. -+ type: string -+ type: object -+ type: array - type: object - skipPhases: - description: SkipPhases is a list of phases to skip during -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -index df222b943..f378c3362 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap.go -@@ -74,8 +74,11 @@ no-proxy = [{{stringsJoin .NoProxyEndpoints "," }}] - {{- end -}} - ` - registryMirrorTemplate = `{{ define "registryMirrorSettings" -}} --[settings.container-registry.mirrors] --"public.ecr.aws" = ["https://{{.RegistryMirrorEndpoint}}"] -+{{- range $orig, $mirror := .RegistryMirrorMap }} -+[[settings.container-registry.mirrors]] -+registry = "{{ $orig }}" -+endpoint = [{{stringsJoin $mirror "," }}] -+{{- end -}} - {{- end -}} - ` - registryMirrorCACertTemplate = `{{ define "registryMirrorCACertSettings" -}} -@@ -88,16 +91,21 @@ trusted=true - // to "public.ecr.aws" rather than the mirror's endpoint - // TODO: Once the bottlerocket fixes are in we need to remove the "public.ecr.aws" creds - registryMirrorCredentialsTemplate = `{{define "registryMirrorCredentialsSettings" -}} -+{{- range $orig, $mirror := .RegistryMirrorMap }} -+{{- if (eq $orig "public.ecr.aws")}} - [[settings.container-registry.credentials]] --registry = "public.ecr.aws" --username = "{{.RegistryMirrorUsername}}" --password = "{{.RegistryMirrorPassword}}" -+registry = "{{ $orig }}" -+username = "{{$.RegistryMirrorUsername}}" -+password = "{{$.RegistryMirrorPassword}}" -+{{- end }} -+{{- end }} - [[settings.container-registry.credentials]] - registry = "{{.RegistryMirrorEndpoint}}" - username = "{{.RegistryMirrorUsername}}" - password = "{{.RegistryMirrorPassword}}" - {{- end -}} - ` -+ - nodeLabelsTemplate = `{{ define "nodeLabelSettings" -}} - [settings.kubernetes.node-labels] - {{.NodeLabels}} -@@ -153,7 +161,7 @@ trusted = true - {{- end -}} - - --{{- if (ne .RegistryMirrorEndpoint "")}} -+{{- if .RegistryMirrorMap}} - {{template "registryMirrorSettings" .}} - {{- end -}} - -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -index 2ee2d942b..ed58dc035 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bootstrap_test.go -@@ -134,8 +134,10 @@ provider-id = "PROVIDERID" - - [settings.network] - hostname = "hostname" --[settings.container-registry.mirrors] --"public.ecr.aws" = ["https://REGISTRY_ENDPOINT"] -+ -+[[settings.container-registry.mirrors]] -+registry = "public.ecr.aws" -+endpoint = ["REGISTRY_ENDPOINT"] - [settings.pki.registry-mirror-ca] - data = "UkVHSVNUUllfQ0E=" - trusted=true` -@@ -162,11 +164,14 @@ provider-id = "PROVIDERID" - - [settings.network] - hostname = "hostname" --[settings.container-registry.mirrors] --"public.ecr.aws" = ["https://REGISTRY_ENDPOINT"] -+ -+[[settings.container-registry.mirrors]] -+registry = "public.ecr.aws" -+endpoint = ["REGISTRY_ENDPOINT"] - [settings.pki.registry-mirror-ca] - data = "UkVHSVNUUllfQ0E=" - trusted=true -+ - [[settings.container-registry.credentials]] - registry = "public.ecr.aws" - username = "admin" -@@ -340,6 +345,39 @@ trusted = true - [settings.pki.bundle2] - data = "MTIzNDU2" - trusted = true` -+ -+ registryMirrorMultipleMirrorsUserData = ` -+[settings.host-containers.admin] -+enabled = true -+superpowered = true -+source = "ADMIN_REPO:ADMIN_TAG" -+user-data = "CnsKCSJzc2giOiB7CgkJImF1dGhvcml6ZWQta2V5cyI6IFsic3NoLXJzYSBBQUEuLi4iXQoJfQp9" -+[settings.host-containers.kubeadm-bootstrap] -+enabled = true -+superpowered = true -+source = "BOOTSTRAP_REPO:BOOTSTRAP_TAG" -+user-data = "Qk9UVExFUk9DS0VUX0JPT1RTVFJBUF9VU0VSREFUQQ==" -+ -+[settings.kubernetes] -+cluster-domain = "cluster.local" -+standalone-mode = true -+authentication-mode = "tls" -+server-tls-bootstrap = false -+pod-infra-container-image = "PAUSE_REPO:PAUSE_TAG" -+provider-id = "PROVIDERID" -+ -+[settings.network] -+hostname = "hostname" -+ -+[[settings.container-registry.mirrors]] -+registry = "docker.io" -+endpoint = ["REGISTRY_ENDPOINT"] -+[[settings.container-registry.mirrors]] -+registry = "public.ecr.aws" -+endpoint = ["REGISTRY_ENDPOINT"] -+[settings.pki.registry-mirror-ca] -+data = "UkVHSVNUUllfQ0E=" -+trusted=true` - ) - - var ( -@@ -622,6 +660,32 @@ func TestGetBottlerocketNodeUserData(t *testing.T) { - }, - output: userDataWithCertBundle, - }, -+ { -+ name: "with multiple registries to mirror", -+ config: &BottlerocketConfig{ -+ BottlerocketAdmin: brAdmin, -+ BottlerocketBootstrap: brBootstrap, -+ Hostname: hostname, -+ Pause: pause, -+ KubeletExtraArgs: map[string]string{ -+ "provider-id": "PROVIDERID", -+ }, -+ RegistryMirrorConfiguration: bootstrapv1.RegistryMirrorConfiguration{ -+ CACert: "REGISTRY_CA", -+ Mirrors: []bootstrapv1.Mirror{ -+ { -+ Registry: "docker.io", -+ Endpoints: []string{"REGISTRY_ENDPOINT"}, -+ }, -+ { -+ Registry: "public.ecr.aws", -+ Endpoints: []string{"REGISTRY_ENDPOINT"}, -+ }, -+ }, -+ }, -+ }, -+ output: registryMirrorMultipleMirrorsUserData, -+ }, - } - for _, testcase := range testcases { - t.Run(testcase.name, func(t *testing.T) { -diff --git a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -index 6e3aaaa95..3e38a7536 100644 ---- a/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -+++ b/bootstrap/kubeadm/internal/bottlerocket/bottlerocket.go -@@ -4,6 +4,7 @@ import ( - "bytes" - "encoding/base64" - "fmt" -+ "regexp" - "strconv" - "strings" - "text/template" -@@ -63,6 +64,7 @@ type BottlerocketSettingsInput struct { - BootstrapContainers []bootstrapv1.BottlerocketBootstrapContainer - SysctlSettings string - CertBundles []bootstrapv1.CertBundle -+ RegistryMirrorMap map[string][]string - } - - // HostPath holds the path and type of a host path volume. -@@ -227,15 +229,14 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot - } - - bottlerocketInput := &BottlerocketSettingsInput{ -- PauseContainerSource: fmt.Sprintf("%s:%s", config.Pause.ImageRepository, config.Pause.ImageTag), -- HTTPSProxyEndpoint: config.ProxyConfiguration.HTTPSProxy, -- RegistryMirrorEndpoint: config.RegistryMirrorConfiguration.Endpoint, -- NodeLabels: parseNodeLabels(config.KubeletExtraArgs["node-labels"]), // empty string if it does not exist -- Taints: parseTaints(config.Taints), // empty string if it does not exist -- ProviderID: config.KubeletExtraArgs["provider-id"], -- Hostname: config.Hostname, -- HostContainers: hostContainers, -- BootstrapContainers: config.BottlerocketCustomBootstrapContainers, -+ PauseContainerSource: fmt.Sprintf("%s:%s", config.Pause.ImageRepository, config.Pause.ImageTag), -+ HTTPSProxyEndpoint: config.ProxyConfiguration.HTTPSProxy, -+ NodeLabels: parseNodeLabels(config.KubeletExtraArgs["node-labels"]), // empty string if it does not exist -+ Taints: parseTaints(config.Taints), // empty string if it does not exist -+ ProviderID: config.KubeletExtraArgs["provider-id"], -+ Hostname: config.Hostname, -+ HostContainers: hostContainers, -+ BootstrapContainers: config.BottlerocketCustomBootstrapContainers, - } - - if len(config.ProxyConfiguration.NoProxy) > 0 { -@@ -243,6 +244,31 @@ func getBottlerocketNodeUserData(bootstrapContainerUserData []byte, users []boot - bottlerocketInput.NoProxyEndpoints = append(bottlerocketInput.NoProxyEndpoints, strconv.Quote(noProxy)) - } - } -+ -+ // When RegistryMirrorConfiguration.Endpoint is specified, we default the mirror to public.ecr.aws. -+ // This was done for backward compatability, since public.ecr.aws was the only supported registry before. -+ // For existing customers this ensures that their nodes dont rollout, unless more mirrors are specified explicitly. -+ // If RegistryMirrorConfiguration.Endpoint is not specified, we iterate the RegistryMirrorConfiguration.Mirrors to setup the mirrors. -+ bottlerocketInput.RegistryMirrorMap = make(map[string][]string) -+ endpointRegex := regexp.MustCompile(`^(https?:\/\/)?[\w\.\:\-]+`) -+ if config.RegistryMirrorConfiguration.Endpoint != "" { -+ bottlerocketInput.RegistryMirrorMap["public.ecr.aws"] = []string{strconv.Quote(config.RegistryMirrorConfiguration.Endpoint)} -+ if endpoint := endpointRegex.FindStringSubmatch(config.RegistryMirrorConfiguration.Endpoint); endpoint != nil { -+ bottlerocketInput.RegistryMirrorEndpoint = endpoint[0] -+ } -+ } else if len(config.RegistryMirrorConfiguration.Mirrors) > 0 { -+ for _, mirror := range config.RegistryMirrorConfiguration.Mirrors { -+ for _, endpoint := range mirror.Endpoints { -+ bottlerocketInput.RegistryMirrorMap[mirror.Registry] = append(bottlerocketInput.RegistryMirrorMap[mirror.Registry], strconv.Quote(endpoint)) -+ } -+ } -+ -+ // Right now we support only one private registry. Hence defaulting to first entry. -+ if endpoint := endpointRegex.FindStringSubmatch(config.RegistryMirrorConfiguration.Mirrors[0].Endpoints[0]); endpoint != nil { -+ bottlerocketInput.RegistryMirrorEndpoint = endpoint[0] -+ } -+ } -+ - if config.RegistryMirrorConfiguration.CACert != "" { - bottlerocketInput.RegistryMirrorCACert = base64.StdEncoding.EncodeToString([]byte(config.RegistryMirrorConfiguration.CACert)) - } -diff --git a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -index f389a5056..51dc3cf19 100644 ---- a/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -+++ b/bootstrap/kubeadm/internal/controllers/kubeadmconfig_controller.go -@@ -489,7 +489,9 @@ func (r *KubeadmConfigReconciler) handleClusterNotInitialized(ctx context.Contex - if scope.Config.Spec.ClusterConfiguration.Proxy.HTTPSProxy != "" { - bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.ClusterConfiguration.Proxy - } -- if scope.Config.Spec.ClusterConfiguration.RegistryMirror.Endpoint != "" { -+ -+ if scope.Config.Spec.ClusterConfiguration.RegistryMirror.Endpoint != "" || -+ len(scope.Config.Spec.ClusterConfiguration.RegistryMirror.Mirrors) != 0 { - bottlerocketConfig.RegistryMirrorConfiguration = scope.Config.Spec.ClusterConfiguration.RegistryMirror - registryUsername, registryPassword, err := r.resolveRegistryCredentials(ctx, scope.Config) - if err != nil { -@@ -717,7 +719,9 @@ func (r *KubeadmConfigReconciler) joinWorker(ctx context.Context, scope *Scope) - if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { - bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy - } -- if scope.Config.Spec.JoinConfiguration.RegistryMirror.Endpoint != "" { -+ -+ if scope.Config.Spec.JoinConfiguration.RegistryMirror.Endpoint != "" || -+ len(scope.Config.Spec.JoinConfiguration.RegistryMirror.Mirrors) != 0 { - bottlerocketConfig.RegistryMirrorConfiguration = scope.Config.Spec.JoinConfiguration.RegistryMirror - registryUsername, registryPassword, err := r.resolveRegistryCredentials(ctx, scope.Config) - if err != nil { -@@ -867,7 +871,9 @@ func (r *KubeadmConfigReconciler) joinControlplane(ctx context.Context, scope *S - if scope.Config.Spec.JoinConfiguration.Proxy.HTTPSProxy != "" { - bottlerocketConfig.ProxyConfiguration = scope.Config.Spec.JoinConfiguration.Proxy - } -- if scope.Config.Spec.ClusterConfiguration.RegistryMirror.Endpoint != "" { -+ -+ if scope.Config.Spec.ClusterConfiguration.RegistryMirror.Endpoint != "" || -+ len(scope.Config.Spec.ClusterConfiguration.RegistryMirror.Mirrors) != 0 { - bottlerocketConfig.RegistryMirrorConfiguration = scope.Config.Spec.ClusterConfiguration.RegistryMirror - registryUsername, registryPassword, err := r.resolveRegistryCredentials(ctx, scope.Config) - if err != nil { -diff --git a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -index 3b12557c4..2f462fbe6 100644 ---- a/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/types/upstreamv1beta2/zz_generated.conversion.go -@@ -1042,6 +1042,7 @@ func Convert_upstreamv1beta2_RegistryMirrorConfiguration_To_v1beta1_RegistryMirr - func autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta2_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { - out.Endpoint = in.Endpoint - out.CACert = in.CACert -+ // INFO: in.Mirrors opted out of conversion generation - return nil - } - -diff --git a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -index 6d812f516..dfff19e2d 100644 ---- a/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -+++ b/bootstrap/kubeadm/types/upstreamv1beta3/zz_generated.conversion.go -@@ -1055,6 +1055,7 @@ func Convert_upstreamv1beta3_RegistryMirrorConfiguration_To_v1beta1_RegistryMirr - func autoConvert_v1beta1_RegistryMirrorConfiguration_To_upstreamv1beta3_RegistryMirrorConfiguration(in *v1beta1.RegistryMirrorConfiguration, out *RegistryMirrorConfiguration, s conversion.Scope) error { - out.Endpoint = in.Endpoint - out.CACert = in.CACert -+ // INFO: in.Mirrors opted out of conversion generation - return nil - } - -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -index 86f387bb9..6cfabed53 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml -@@ -1971,6 +1971,27 @@ spec: - description: Endpoint defines the registry mirror endpoint - to use for pulling images - type: string -+ mirrors: -+ description: Mirrors defines a list of image registry -+ mirrors. -+ items: -+ description: Mirror holds the settings for mirroring -+ a registry. -+ properties: -+ endpoints: -+ description: Endpoints defines the registry mirror -+ endpoints to use for pulling images. Currently -+ we support only one private registry. Hence endpoints -+ would have only one entry. -+ items: -+ type: string -+ type: array -+ registry: -+ description: Registry defines the registry we are -+ mirroring to the endpoint. -+ type: string -+ type: object -+ type: array - type: object - scheduler: - description: Scheduler contains extra settings for the scheduler -@@ -2862,6 +2883,27 @@ spec: - description: Endpoint defines the registry mirror endpoint - to use for pulling images - type: string -+ mirrors: -+ description: Mirrors defines a list of image registry -+ mirrors. -+ items: -+ description: Mirror holds the settings for mirroring -+ a registry. -+ properties: -+ endpoints: -+ description: Endpoints defines the registry mirror -+ endpoints to use for pulling images. Currently -+ we support only one private registry. Hence endpoints -+ would have only one entry. -+ items: -+ type: string -+ type: array -+ registry: -+ description: Registry defines the registry we are -+ mirroring to the endpoint. -+ type: string -+ type: object -+ type: array - type: object - skipPhases: - description: SkipPhases is a list of phases to skip during -diff --git a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -index 9a2228488..2791830fd 100644 ---- a/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -+++ b/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanetemplates.yaml -@@ -1955,6 +1955,28 @@ spec: - description: Endpoint defines the registry mirror - endpoint to use for pulling images - type: string -+ mirrors: -+ description: Mirrors defines a list of image registry -+ mirrors. -+ items: -+ description: Mirror holds the settings for mirroring -+ a registry. -+ properties: -+ endpoints: -+ description: Endpoints defines the registry -+ mirror endpoints to use for pulling images. -+ Currently we support only one private -+ registry. Hence endpoints would have only -+ one entry. -+ items: -+ type: string -+ type: array -+ registry: -+ description: Registry defines the registry -+ we are mirroring to the endpoint. -+ type: string -+ type: object -+ type: array - type: object - scheduler: - description: Scheduler contains extra settings for -@@ -2907,6 +2929,28 @@ spec: - description: Endpoint defines the registry mirror - endpoint to use for pulling images - type: string -+ mirrors: -+ description: Mirrors defines a list of image registry -+ mirrors. -+ items: -+ description: Mirror holds the settings for mirroring -+ a registry. -+ properties: -+ endpoints: -+ description: Endpoints defines the registry -+ mirror endpoints to use for pulling images. -+ Currently we support only one private -+ registry. Hence endpoints would have only -+ one entry. -+ items: -+ type: string -+ type: array -+ registry: -+ description: Registry defines the registry -+ we are mirroring to the endpoint. -+ type: string -+ type: object -+ type: array - type: object - skipPhases: - description: SkipPhases is a list of phases to skip --- -2.34.1 - diff --git a/projects/kubernetes-sigs/cluster-api/patches/0041-Use-controller-runtime-patch-for-restmapper-cache.patch b/projects/kubernetes-sigs/cluster-api/patches/0039-Use-controller-runtime-patch-for-restmapper-cache.patch similarity index 69% rename from projects/kubernetes-sigs/cluster-api/patches/0041-Use-controller-runtime-patch-for-restmapper-cache.patch rename to projects/kubernetes-sigs/cluster-api/patches/0039-Use-controller-runtime-patch-for-restmapper-cache.patch index 60a3d93b61..90dd3f6649 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0041-Use-controller-runtime-patch-for-restmapper-cache.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0039-Use-controller-runtime-patch-for-restmapper-cache.patch @@ -1,7 +1,7 @@ -From 3f900f5d9fadf763fa10b198c778e05d19a0f9cb Mon Sep 17 00:00:00 2001 +From 6bf3a03319f1f519850a27ad7025f926058c08d8 Mon Sep 17 00:00:00 2001 From: Guillermo Gaston Date: Thu, 15 Feb 2024 15:04:46 +0000 -Subject: [PATCH 40/40] Use controller-runtime patch for restmapper cache +Subject: [PATCH 39/40] Use controller-runtime patch for restmapper cache This fixes the issue with a race condition when making v1alpha4 not served. @@ -9,18 +9,27 @@ served. Using a merged but unreleased change. Will update to the release tag once this is cut. --- - go.mod | 2 ++ + go.mod | 4 +++- go.sum | 4 ++-- - hack/tools/go.mod | 2 ++ + hack/tools/go.mod | 4 +++- hack/tools/go.sum | 4 ++-- - test/go.mod | 2 ++ + test/go.mod | 4 +++- test/go.sum | 4 ++-- - 6 files changed, 12 insertions(+), 6 deletions(-) + 6 files changed, 15 insertions(+), 9 deletions(-) diff --git a/go.mod b/go.mod -index 7aa6a0993..3c0e9d880 100644 +index ba3c3b280..170f5a70f 100644 --- a/go.mod +++ b/go.mod +@@ -46,7 +46,7 @@ require ( + k8s.io/kube-openapi v0.0.0-20230717233707-2695361300d9 + k8s.io/kubectl v0.28.4 + k8s.io/utils v0.0.0-20230406110748-d93618cff8a2 +- sigs.k8s.io/controller-runtime v0.16.5 ++ sigs.k8s.io/controller-runtime v0.17.3 + sigs.k8s.io/yaml v1.4.0 + ) + @@ -185,3 +185,5 @@ require ( sigs.k8s.io/kustomize/kyaml v0.14.3-0.20230601165947-6ce0bf390ce3 // indirect sigs.k8s.io/structured-merge-diff/v4 v4.2.3 // indirect @@ -28,24 +37,33 @@ index 7aa6a0993..3c0e9d880 100644 + +replace sigs.k8s.io/controller-runtime => sigs.k8s.io/controller-runtime v0.16.5-0.20240215143111-dca5e8b2b00a diff --git a/go.sum b/go.sum -index 912d9645d..8239a813a 100644 +index ee115a17c..cc8887cc3 100644 --- a/go.sum +++ b/go.sum @@ -1042,8 +1042,8 @@ rsc.io/quote/v3 v3.1.0/go.mod h1:yEA65RcK8LyAZtP9Kv3t0HmxON59tX3rD+tICJqUlj0= rsc.io/sampler v1.3.0/go.mod h1:T1hPZKmBbMNahiBKFy5HrXp6adAjACjK9JXDnKaTXpA= sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.1.2 h1:trsWhjU5jZrx6UvFu4WzQDrN7Pga4a7Qg+zcfcj64PA= sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.1.2/go.mod h1:+qG7ISXqCDVVcyO8hLn12AKVYYUjM7ftlqsqmrhMZE0= --sigs.k8s.io/controller-runtime v0.16.3 h1:2TuvuokmfXvDUamSx1SuAOO3eTyye+47mJCigwG62c4= --sigs.k8s.io/controller-runtime v0.16.3/go.mod h1:j7bialYoSn142nv9sCOJmQgDXQXxnroFU4VnX/brVJ0= +-sigs.k8s.io/controller-runtime v0.16.5 h1:yr1cEJbX08xsTW6XEIzT13KHHmIyX8Umvme2cULvFZw= +-sigs.k8s.io/controller-runtime v0.16.5/go.mod h1:j7bialYoSn142nv9sCOJmQgDXQXxnroFU4VnX/brVJ0= +sigs.k8s.io/controller-runtime v0.16.5-0.20240215143111-dca5e8b2b00a h1:1veEwfhXsw2Afqx7EkhS9wOslyLuw6O8sRfGx23PfWs= +sigs.k8s.io/controller-runtime v0.16.5-0.20240215143111-dca5e8b2b00a/go.mod h1:j7bialYoSn142nv9sCOJmQgDXQXxnroFU4VnX/brVJ0= sigs.k8s.io/json v0.0.0-20221116044647-bc3834ca7abd h1:EDPBXCAspyGV4jQlpZSudPeMmr1bNJefnuqLsRAsHZo= sigs.k8s.io/json v0.0.0-20221116044647-bc3834ca7abd/go.mod h1:B8JuhiUyNFVKdsE8h686QcCxMaH6HrOAZj4vswFpcB0= sigs.k8s.io/kustomize/api v0.13.5-0.20230601165947-6ce0bf390ce3 h1:XX3Ajgzov2RKUdc5jW3t5jwY7Bo7dcRm+tFxT+NfgY0= diff --git a/hack/tools/go.mod b/hack/tools/go.mod -index 24e7ab32c..c7aa64ca4 100644 +index 4f789d23d..918e34c52 100644 --- a/hack/tools/go.mod +++ b/hack/tools/go.mod +@@ -22,7 +22,7 @@ require ( + k8s.io/utils v0.0.0-20230406110748-d93618cff8a2 + sigs.k8s.io/cluster-api v0.0.0-00010101000000-000000000000 + sigs.k8s.io/cluster-api/test v0.0.0-00010101000000-000000000000 +- sigs.k8s.io/controller-runtime v0.16.5 ++ sigs.k8s.io/controller-runtime v0.17.3 + sigs.k8s.io/controller-tools v0.13.0 + sigs.k8s.io/kubebuilder/docs/book/utils v0.0.0-20211028165026-57688c578b5d + sigs.k8s.io/kustomize/api v0.13.5-0.20230601165947-6ce0bf390ce3 @@ -139,3 +139,5 @@ require ( sigs.k8s.io/kustomize/kyaml v0.14.3-0.20230601165947-6ce0bf390ce3 // indirect sigs.k8s.io/structured-merge-diff/v4 v4.2.3 // indirect @@ -53,24 +71,33 @@ index 24e7ab32c..c7aa64ca4 100644 + +replace sigs.k8s.io/controller-runtime => sigs.k8s.io/controller-runtime v0.16.5-0.20240215143111-dca5e8b2b00a diff --git a/hack/tools/go.sum b/hack/tools/go.sum -index e0e2b7c89..a3f48c117 100644 +index 70a2716c3..483a274e1 100644 --- a/hack/tools/go.sum +++ b/hack/tools/go.sum @@ -747,8 +747,8 @@ k8s.io/utils v0.0.0-20230406110748-d93618cff8a2/go.mod h1:OLgZIPagt7ERELqWJFomSt rsc.io/binaryregexp v0.2.0/go.mod h1:qTv7/COck+e2FymRvadv62gMdZztPaShugOCi3I+8D8= rsc.io/quote/v3 v3.1.0/go.mod h1:yEA65RcK8LyAZtP9Kv3t0HmxON59tX3rD+tICJqUlj0= rsc.io/sampler v1.3.0/go.mod h1:T1hPZKmBbMNahiBKFy5HrXp6adAjACjK9JXDnKaTXpA= --sigs.k8s.io/controller-runtime v0.16.3 h1:2TuvuokmfXvDUamSx1SuAOO3eTyye+47mJCigwG62c4= --sigs.k8s.io/controller-runtime v0.16.3/go.mod h1:j7bialYoSn142nv9sCOJmQgDXQXxnroFU4VnX/brVJ0= +-sigs.k8s.io/controller-runtime v0.16.5 h1:yr1cEJbX08xsTW6XEIzT13KHHmIyX8Umvme2cULvFZw= +-sigs.k8s.io/controller-runtime v0.16.5/go.mod h1:j7bialYoSn142nv9sCOJmQgDXQXxnroFU4VnX/brVJ0= +sigs.k8s.io/controller-runtime v0.16.5-0.20240215143111-dca5e8b2b00a h1:1veEwfhXsw2Afqx7EkhS9wOslyLuw6O8sRfGx23PfWs= +sigs.k8s.io/controller-runtime v0.16.5-0.20240215143111-dca5e8b2b00a/go.mod h1:j7bialYoSn142nv9sCOJmQgDXQXxnroFU4VnX/brVJ0= sigs.k8s.io/controller-tools v0.13.0 h1:NfrvuZ4bxyolhDBt/rCZhDnx3M2hzlhgo5n3Iv2RykI= sigs.k8s.io/controller-tools v0.13.0/go.mod h1:5vw3En2NazbejQGCeWKRrE7q4P+CW8/klfVqP8QZkgA= sigs.k8s.io/json v0.0.0-20221116044647-bc3834ca7abd h1:EDPBXCAspyGV4jQlpZSudPeMmr1bNJefnuqLsRAsHZo= diff --git a/test/go.mod b/test/go.mod -index 3df0e722b..b13a67f13 100644 +index 19efdde6a..f261a9ab5 100644 --- a/test/go.mod +++ b/test/go.mod +@@ -32,7 +32,7 @@ require ( + k8s.io/klog/v2 v2.100.1 + k8s.io/utils v0.0.0-20230406110748-d93618cff8a2 + sigs.k8s.io/cluster-api v0.0.0-00010101000000-000000000000 +- sigs.k8s.io/controller-runtime v0.16.5 ++ sigs.k8s.io/controller-runtime v0.17.3 + sigs.k8s.io/kind v0.20.0 + sigs.k8s.io/yaml v1.4.0 + ) @@ -161,3 +161,5 @@ require ( sigs.k8s.io/json v0.0.0-20221116044647-bc3834ca7abd // indirect sigs.k8s.io/structured-merge-diff/v4 v4.2.3 // indirect @@ -78,20 +105,20 @@ index 3df0e722b..b13a67f13 100644 + +replace sigs.k8s.io/controller-runtime => sigs.k8s.io/controller-runtime v0.16.5-0.20240215143111-dca5e8b2b00a diff --git a/test/go.sum b/test/go.sum -index 88c1ca288..226708e02 100644 +index 6b1db2c3d..f10734c8a 100644 --- a/test/go.sum +++ b/test/go.sum @@ -865,8 +865,8 @@ rsc.io/quote/v3 v3.1.0/go.mod h1:yEA65RcK8LyAZtP9Kv3t0HmxON59tX3rD+tICJqUlj0= rsc.io/sampler v1.3.0/go.mod h1:T1hPZKmBbMNahiBKFy5HrXp6adAjACjK9JXDnKaTXpA= sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.1.2 h1:trsWhjU5jZrx6UvFu4WzQDrN7Pga4a7Qg+zcfcj64PA= sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.1.2/go.mod h1:+qG7ISXqCDVVcyO8hLn12AKVYYUjM7ftlqsqmrhMZE0= --sigs.k8s.io/controller-runtime v0.16.3 h1:2TuvuokmfXvDUamSx1SuAOO3eTyye+47mJCigwG62c4= --sigs.k8s.io/controller-runtime v0.16.3/go.mod h1:j7bialYoSn142nv9sCOJmQgDXQXxnroFU4VnX/brVJ0= +-sigs.k8s.io/controller-runtime v0.16.5 h1:yr1cEJbX08xsTW6XEIzT13KHHmIyX8Umvme2cULvFZw= +-sigs.k8s.io/controller-runtime v0.16.5/go.mod h1:j7bialYoSn142nv9sCOJmQgDXQXxnroFU4VnX/brVJ0= +sigs.k8s.io/controller-runtime v0.16.5-0.20240215143111-dca5e8b2b00a h1:1veEwfhXsw2Afqx7EkhS9wOslyLuw6O8sRfGx23PfWs= +sigs.k8s.io/controller-runtime v0.16.5-0.20240215143111-dca5e8b2b00a/go.mod h1:j7bialYoSn142nv9sCOJmQgDXQXxnroFU4VnX/brVJ0= sigs.k8s.io/json v0.0.0-20221116044647-bc3834ca7abd h1:EDPBXCAspyGV4jQlpZSudPeMmr1bNJefnuqLsRAsHZo= sigs.k8s.io/json v0.0.0-20221116044647-bc3834ca7abd/go.mod h1:B8JuhiUyNFVKdsE8h686QcCxMaH6HrOAZj4vswFpcB0= sigs.k8s.io/kind v0.20.0 h1:f0sc3v9mQbGnjBUaqSFST1dwIuiikKVGgoTwpoP33a8= -- -2.39.3 (Apple Git-145) +2.42.0 diff --git a/projects/kubernetes-sigs/cluster-api/patches/0042-enable-kubeadm-feature-flags-mutation.patch b/projects/kubernetes-sigs/cluster-api/patches/0040-enable-kubeadm-feature-flags-mutation.patch similarity index 99% rename from projects/kubernetes-sigs/cluster-api/patches/0042-enable-kubeadm-feature-flags-mutation.patch rename to projects/kubernetes-sigs/cluster-api/patches/0040-enable-kubeadm-feature-flags-mutation.patch index af1f472069..6ca324af88 100644 --- a/projects/kubernetes-sigs/cluster-api/patches/0042-enable-kubeadm-feature-flags-mutation.patch +++ b/projects/kubernetes-sigs/cluster-api/patches/0040-enable-kubeadm-feature-flags-mutation.patch @@ -1,7 +1,7 @@ -From f478ad851ae6b6d1c6465a828eecb8195a30d880 Mon Sep 17 00:00:00 2001 +From f7e923a4afa5d8db796dd3cb0d06896ba3bb3911 Mon Sep 17 00:00:00 2001 From: Abhinav Pandey Date: Tue, 27 Feb 2024 22:37:00 -0800 -Subject: [PATCH] enable kubeadm feature flags mutation +Subject: [PATCH 40/40] enable kubeadm feature flags mutation --- .../internal/controllers/controller_test.go | 3 +-