diff --git a/docs/api-reference/core.md b/docs/api-reference/core.md index 2548031faaf..d691a27b9d0 100644 --- a/docs/api-reference/core.md +++ b/docs/api-reference/core.md @@ -471,6 +471,19 @@ Bastion +
status
+
+
+CloudProfileStatus
+
+
+Status contains the current status of the cloud profile.
++(Appears on: +CloudProfile) +
++
CloudProfileStatus contains the status of the cloud profile.
+ +Field | +Description | +
---|---|
+kubernetesVersions
+
+
+[]ExpirableVersionStatus
+
+
+ |
+
+ KubernetesVersions contains the statuses of the kubernetes versions. + |
+
+machineImageVersions
+
+
+[]MachineImageVersionStatus
+
+
+ |
+
+ MachineImageVersions contains the statuses of the machine image versions. + |
+
@@ -5110,7 +5168,7 @@ Kubernetes meta/v1.Time
ExpirationDate defines the time at which this version expires.
+Deprecated: Is replaced by Lifecycle.
Classification defines the state of a version (preview, supported, deprecated)
+Classification defines the state of a version (preview, supported, deprecated). +Deprecated: Is replaced by Lifecycle.
+lifecycle
+
+
+[]LifecycleStage
+
+
+Lifecycle defines the lifecycle stages for this version. Cannot be used in combination with Classification and ExpirationDate.
++(Appears on: +CloudProfileStatus, +MachineImageVersionStatus) +
++
ExpirableVersionStatus defines the current status of an expirable version.
+ +Field | +Description | +
---|---|
+version
+
+string
+
+ |
+
+ Version is the version identifier. + |
+
+classificationState
+
+
+VersionClassification
+
+
+ |
+
+ ClassificationState reflects the current state in the classification lifecycle. |
Field | +Description | +
---|---|
+classification
+
+
+VersionClassification
+
+
+ |
+
+ Classification is the category of this lifecycle stage (unavailable, preview, supported, deprecated, expired). + |
+
+startTime
+
+
+Kubernetes meta/v1.Time
+
+
+ |
+
+(Optional)
+ StartTime defines when this lifecycle stage becomes active. + |
+
@@ -7894,6 +8056,48 @@ Examples:
+(Appears on: +CloudProfileStatus) +
++
+Field | +Description | +
---|---|
+name
+
+string
+
+ |
+
+ Name matches the name of the MachineImage the status is represented of. + |
+
+versions
+
+
+[]ExpirableVersionStatus
+
+
+ |
+
+ Versions contains the statuses of the machine image versions. + |
+
@@ -13160,7 +13364,9 @@ string
(string
alias)
(Appears on: -ExpirableVersion) +ExpirableVersion, +ExpirableVersionStatus, +LifecycleStage)
VersionClassification is the logical state of a version.
diff --git a/docs/usage/shoot-operations/shoot_versions.md b/docs/usage/shoot-operations/shoot_versions.md index f232ad51ad9..85f0cb3c0ad 100644 --- a/docs/usage/shoot-operations/shoot_versions.md +++ b/docs/usage/shoot-operations/shoot_versions.md @@ -35,16 +35,44 @@ Moreover, this allows Gardener to "understand" the current state of a version an - I can determine the time when my Shoot clusters Machine image and Kubernetes version will be forcefully updated to the next patch or minor version (in case the cluster is running a deprecated version with an expiration date). - I can get this information via API from the `CloudProfile`. -## Version Classifications +## Version Classification Lifecycles + +Kubernetes and machine image versions in the `CloudProfile` are classified into individual stages: `unavailable`, `preview`, `supported`, `deprecated`, and `expired`. + +Administrators may define a classification lifecycle, promoting versions through these lifecycle stages depending on time. The current classification stage is evaluated by the cloud profile reconciler and patched into the `status` subresource of the `CloudProfile`. If an administrator does not specify a classification lifecycle, the version defaults to `supported`. -Administrators can classify versions into four distinct "logical states": `preview`, `supported`, `deprecated`, and `expired`. The version classification serves as a "point-of-reference" for end-users and also has implications during shoot creation and the maintenance time. -If a version is unclassified, Gardener cannot make those decision based on the "logical state". -Nevertheless, Gardener can operate without version classifications and can be added at any time to the Kubernetes and machine image versions in the `CloudProfile`. +As a best practice, versions usually start with the classification `preview`, then are promoted to `supported`, eventually `deprecated` and finally `expired`. Here is an example: -As a best practice, versions usually start with the classification `preview`, then are promoted to `supported`, eventually `deprecated` and finally `expired`. -This information is programmatically available in the `CloudProfiles` of the Garden cluster. +```yaml +# assume that the current date is 2024-12-03 +apiVersion: core.gardener.cloud/v1beta1 +kind: CloudProfile +metadata: + name: local +spec: + kubernetes: + versions: + - version: 1.30.6 + lifecycle: + - classification: preview # starts in preview because no start time is defined + - classification: supported + startTime: "2024-12-01T00:00:00Z" + - classification: deprecated + startTime: "2025-03-01T00:00:00Z" + - classification: expired + startTime: "2025-04-01T00:00:00Z" +status: + kubernetes: + versions: + - version: 1.30.6 + classificationState: supported +``` + +The classification stages must occur in a specific order and the start time must reflect this order. Here is a list of the available classification stages in the order they can appear: + +- **unavailable:** An `unavailable` version is planned to become available in the future. It is not possible to reference this version in this stage and can be used by administrators to schedule a new version release. Usually there is no need to explicitly declare this stage in the classification lifecycle because it can be automatically derived when the current time is before the first specified lifecycle stage. - **preview:** A `preview` version is a new version that has not yet undergone thorough testing, possibly a new release, and needs time to be validated. Due to its short early age, there is a higher probability of undiscovered issues and is therefore not yet recommended for production usage. @@ -60,39 +88,59 @@ Typically for Kubernetes versions, the latest Kubernetes patch versions of the a New Shoots should not use this version anymore. Existing Shoots will be updated to a newer version if `auto-update` is enabled (`.spec.maintenance.autoUpdate.kubernetesVersion` for Kubernetes version `auto-update`, or `.spec.maintenance.autoUpdate.machineImageVersion` for machine image version `auto-update`). Using automatic upgrades, however, does not guarantee that a Shoot runs a non-deprecated version, as the latest version (overall or of the minor version) can be deprecated as well. -Deprecated versions **should** have an expiration date set for eventual expiration. -- **expired:** An `expired` versions has an expiration date (based on the [Golang time package](https://golang.org/src/time/time.go)) in the past. -New clusters with that version cannot be created and existing clusters are forcefully migrated to a higher version during the maintenance time. +- **expired:** An `expired` version cannot be used to create a new cluster and existing clusters are forcefully migrated to a higher version during the maintenance time. -Below is an example how the relevant section of the `CloudProfile` might look like: +Below is a more complex example illustrating different scenarios for lifecycle classifications: -``` yaml +```yaml apiVersion: core.gardener.cloud/v1beta1 kind: CloudProfile metadata: - name: alicloud + name: local spec: kubernetes: versions: - - classification: preview - version: 1.27.0 - - classification: preview - version: 1.26.3 - - classification: supported - version: 1.26.2 - - classification: preview - version: 1.25.5 - - classification: supported - version: 1.25.4 - - classification: supported - version: 1.24.6 - - classification: deprecated - expirationDate: "2022-11-30T23:59:59Z" - version: 1.24.5 + # if an administrator deploys just the version without any lifecycle, + # the reconciler will evaluate the classification status to supported + - version: 1.27.0 + + # when introducing a new version it may not contain any deprecation or expiration date yet + - version: 1.28.0 + lifecycle: + - classification: preview + - classification: supported + startTime: 2024-12-01T00:00:00Z" + + # it is not strictly required that every lifecycle stage must occur, + # they can also be dropped as long as their general order is maintained + - version: 1.18.0 + lifecycle: + - classification: supported + - classification: expired + startTime: 2022-06-01T00:00:00Z" + + # to schedule a new version release, the administrator can define the start times + # of all lifecycle events in the future, such that the classification status will + # be evaluated to unavailable + - version: 2.0.0 + lifecycle: + - classification: preview + startTime: 2036-02-07T06:28:16Z" +status: + kubernetes: + versions: + - version: 1.27.0 + classificationState: supported + - version: 1.28.0 + classificationState: supported + - version: 1.18.0 + classificationState: expired + - version: 2.0.0 + classificationState: unavailable ``` -## Automatic Version Upgrades +## Automatic Version Upgrades There are two ways, the Kubernetes version of the control plane as well as the Kubernetes and machine image version of a worker pool can be upgraded: `auto update` and `forceful` update. See [Automatic Version Updates](../shoot/shoot_maintenance.md#automatic-version-updates) for how to enable `auto updates` for Kubernetes or machine image versions on the Shoot cluster. @@ -104,7 +152,7 @@ This happens **even if the owner has opted out of automatic cluster updates!** - The `Shoot` has auto-update enabled and the version is not the *latest eligible version* for the auto-update. Please note that this *latest version* that qualifies for an auto-update is not necessarily the overall latest version in the CloudProfile: - For Kubernetes version, the latest eligible version for auto-updates is the latest patch version of the current minor. - For machine image version, the latest eligible version for auto-updates is controlled by the `updateStrategy` field of the machine image in the CloudProfile. -- The `Shoot` has auto-update disabled and the version is either expired or does not exist. +- The `Shoot` has auto-update disabled and the version is either expired or does not exist. The auto update can fail if the version is already on the *latest eligible version* for the auto-update. A failed auto update triggers a **force update**. The force and auto update path for Kubernetes and machine image versions differ slightly and are described in more detail below. @@ -135,7 +183,7 @@ machineImages: - name: suse-chost updateStrategy: patch versions: - - version: 15.3.20220818 + - version: 15.3.20220818 - version: 15.3.20221118 ``` diff --git a/extensions/pkg/bastion/machine.go b/extensions/pkg/bastion/machine.go index e8e43b72a37..72c122640ef 100644 --- a/extensions/pkg/bastion/machine.go +++ b/extensions/pkg/bastion/machine.go @@ -14,6 +14,7 @@ import ( "k8s.io/utils/ptr" gardencorev1beta1 "github.com/gardener/gardener/pkg/apis/core/v1beta1" + "github.com/gardener/gardener/pkg/apis/core/v1beta1/helper" ) // MachineSpec define all bastion vm details derived from the CloudProfile @@ -85,7 +86,7 @@ func getImageArchitectures(bastion *gardencorev1beta1.Bastion, images []gardenco return } - if version.Classification != nil && *version.Classification == gardencorev1beta1.ClassificationSupported { + if helper.VersionIsSupported(version.ExpirableVersion) { for _, arch := range version.Architectures { architectures.Insert(arch) } @@ -124,7 +125,7 @@ func getImageName(bastion *gardencorev1beta1.Bastion, images []gardencorev1beta1 // take the first image from cloud profile that is supported and arch compatible for _, image := range images { for _, version := range image.Versions { - if version.Classification == nil || *version.Classification != gardencorev1beta1.ClassificationSupported { + if !helper.VersionIsSupported(version.ExpirableVersion) { continue } if !slices.Contains(version.Architectures, arch) { @@ -153,7 +154,7 @@ func getImageVersion(bastion *gardencorev1beta1.Bastion, imageName, machineArch return "", fmt.Errorf("image version %s not found not found in cloudProfile", *bastion.MachineImage.Version) } - if image.Versions[versionIndex].Classification != nil && *image.Versions[versionIndex].Classification != gardencorev1beta1.ClassificationSupported { + if !helper.VersionIsSupported(image.Versions[versionIndex].ExpirableVersion) { return "", fmt.Errorf("specified image %s in version %s is not classified supported", imageName, *bastion.MachineImage.Version) } @@ -162,7 +163,7 @@ func getImageVersion(bastion *gardencorev1beta1.Bastion, imageName, machineArch var greatest *semver.Version for _, version := range image.Versions { - if version.Classification == nil || *version.Classification != gardencorev1beta1.ClassificationSupported { + if !helper.VersionIsSupported(version.ExpirableVersion) { continue } diff --git a/pkg/apis/core/helper/cloudprofile.go b/pkg/apis/core/helper/cloudprofile.go new file mode 100644 index 00000000000..7f276d3713f --- /dev/null +++ b/pkg/apis/core/helper/cloudprofile.go @@ -0,0 +1,71 @@ +package helper + +import ( + "time" + + "github.com/gardener/gardener/pkg/apis/core" +) + +func CurrentLifecycleClassification(version core.ExpirableVersion) core.VersionClassification { + var ( + currentClassification = core.ClassificationUnavailable + currentTime = time.Now() + ) + + if version.Classification != nil || version.ExpirationDate != nil { + // old cloud profile definition, convert to lifecycle + // this can be removed as soon as we remove the old classification and expiration date fields + + if version.Classification != nil { + version.Lifecycle = append(version.Lifecycle, core.LifecycleStage{ + Classification: *version.Classification, + }) + } + + if version.ExpirationDate != nil { + if version.Classification == nil { + version.Lifecycle = append(version.Lifecycle, core.LifecycleStage{ + Classification: core.ClassificationSupported, + }) + } + + version.Lifecycle = append(version.Lifecycle, core.LifecycleStage{ + Classification: core.ClassificationExpired, + StartTime: version.ExpirationDate, + }) + } + } + + if len(version.Lifecycle) == 0 { + // when there is no classification lifecycle defined then default to supported + version.Lifecycle = append(version.Lifecycle, core.LifecycleStage{ + Classification: core.ClassificationSupported, + }) + } + + for _, stage := range version.Lifecycle { + startTime := time.Time{} + if stage.StartTime != nil { + startTime = stage.StartTime.Time + } + + if startTime.Before(currentTime) { + currentClassification = stage.Classification + } + } + + return currentClassification +} + +func VersionIsSupported(version core.ExpirableVersion) bool { + return CurrentLifecycleClassification(version) == core.ClassificationSupported +} + +func SupportedLifecycleClassification(version core.ExpirableVersion) *core.LifecycleStage { + for _, stage := range version.Lifecycle { + if stage.Classification == core.ClassificationSupported { + return &stage + } + } + return nil +} diff --git a/pkg/apis/core/helper/cloudprofile_test.go b/pkg/apis/core/helper/cloudprofile_test.go new file mode 100644 index 00000000000..84623b95d97 --- /dev/null +++ b/pkg/apis/core/helper/cloudprofile_test.go @@ -0,0 +1,154 @@ +package helper_test + +import ( + "time" + + . "github.com/onsi/ginkgo/v2" + . "github.com/onsi/gomega" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/utils/ptr" + + "github.com/gardener/gardener/pkg/apis/core" + "github.com/gardener/gardener/pkg/apis/core/helper" +) + +var _ = Describe("CloudProfile Helper", func() { + var ( + now = time.Now() + ) + + Context("calculate the current lifecycle classification", func() { + It("only version is given", func() { + classification := helper.CurrentLifecycleClassification(core.ExpirableVersion{ + Version: "1.28.0", + }) + Expect(classification).To(Equal(core.ClassificationSupported)) + }) + + It("unavailable classification due to scheduled lifecycle start in the future", func() { + classification := helper.CurrentLifecycleClassification(core.ExpirableVersion{ + Version: "1.28.0", + Lifecycle: []core.LifecycleStage{ + { + Classification: core.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(3 * time.Hour))), + }, + }, + }) + Expect(classification).To(Equal(core.ClassificationUnavailable)) + }) + + It("version is in preview stage", func() { + classification := helper.CurrentLifecycleClassification(core.ExpirableVersion{ + Version: "1.28.0", + Lifecycle: []core.LifecycleStage{ + { + Classification: core.ClassificationPreview, + StartTime: ptr.To(metav1.NewTime(now.Add(-1 * time.Hour))), + }, + { + Classification: core.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(3 * time.Hour))), + }, + }, + }) + Expect(classification).To(Equal(core.ClassificationPreview)) + }) + + It("full version lifecycle with version currently in supported stage", func() { + classification := helper.CurrentLifecycleClassification(core.ExpirableVersion{ + Version: "1.28.0", + Lifecycle: []core.LifecycleStage{ + { + Classification: core.ClassificationPreview, + StartTime: ptr.To(metav1.NewTime(now.Add(-3 * time.Hour))), + }, + { + Classification: core.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(-1 * time.Hour))), + }, + { + Classification: core.ClassificationDeprecated, + StartTime: ptr.To(metav1.NewTime(now.Add(5 * time.Hour))), + }, + { + Classification: core.ClassificationExpired, + StartTime: ptr.To(metav1.NewTime(now.Add(8 * time.Hour))), + }, + }, + }) + Expect(classification).To(Equal(core.ClassificationSupported)) + }) + + It("version is expired", func() { + classification := helper.CurrentLifecycleClassification(core.ExpirableVersion{ + Version: "1.28.0", + Lifecycle: []core.LifecycleStage{ + { + Classification: core.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(-4 * time.Hour))), + }, + { + Classification: core.ClassificationDeprecated, + StartTime: ptr.To(metav1.NewTime(now.Add(-3 * time.Hour))), + }, + { + Classification: core.ClassificationExpired, + StartTime: ptr.To(metav1.NewTime(now.Add(-1 * time.Hour))), + }, + }, + }) + Expect(classification).To(Equal(core.ClassificationExpired)) + }) + + It("first lifecycle start time field is optional", func() { + classification := helper.CurrentLifecycleClassification(core.ExpirableVersion{ + Version: "1.28.5", + Lifecycle: []core.LifecycleStage{ + { + Classification: core.ClassificationPreview, + }, + { + Classification: core.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(3 * time.Hour))), + }, + { + Classification: core.ClassificationDeprecated, + StartTime: ptr.To(metav1.NewTime(now.Add(4 * time.Hour))), + }, + { + Classification: core.ClassificationExpired, + StartTime: ptr.To(metav1.NewTime(now.Add(5 * time.Hour))), + }, + }, + }) + Expect(classification).To(Equal(core.ClassificationPreview)) + }) + + It("determining supported for deprecated classification field", func() { + classification := helper.CurrentLifecycleClassification(core.ExpirableVersion{ + Classification: ptr.To(core.ClassificationSupported), + Version: "1.28.0", + }) + Expect(classification).To(Equal(core.ClassificationSupported)) + }) + + It("determining expired for deprecated expiration date field", func() { + classification := helper.CurrentLifecycleClassification(core.ExpirableVersion{ + ExpirationDate: ptr.To(metav1.NewTime(now.Add(-1 * time.Hour))), + Version: "1.28.0", + }) + Expect(classification).To(Equal(core.ClassificationExpired)) + }) + + It("determining preview for deprecated classification and expiration date field", func() { + classification := helper.CurrentLifecycleClassification(core.ExpirableVersion{ + Classification: ptr.To(core.ClassificationPreview), + Version: "1.28.0", + ExpirationDate: ptr.To(metav1.NewTime(now.Add(3 * time.Hour))), + }) + Expect(classification).To(Equal(core.ClassificationPreview)) + }) + + }) +}) diff --git a/pkg/apis/core/helper/helpers.go b/pkg/apis/core/helper/helpers.go index 54223a6d730..cdc26e88a7a 100644 --- a/pkg/apis/core/helper/helpers.go +++ b/pkg/apis/core/helper/helpers.go @@ -7,6 +7,7 @@ package helper import ( "errors" "fmt" + "slices" "strconv" "strings" @@ -318,12 +319,23 @@ func getVersionDiff(v1, v2 []core.ExpirableVersion) map[string]int { return diff } +type MachineImageDiff struct { + RemovedImages sets.Set[string] + RemovedVersions map[string]sets.Set[string] + RemovedVersionClassifications map[string]map[string][]core.VersionClassification + AddedImages sets.Set[string] + AddedVersions map[string]sets.Set[string] +} + // GetMachineImageDiff returns the removed and added machine images and versions from the diff of two slices. -func GetMachineImageDiff(old, new []core.MachineImage) (removedMachineImages sets.Set[string], removedMachineImageVersions map[string]sets.Set[string], addedMachineImages sets.Set[string], addedMachineImageVersions map[string]sets.Set[string]) { - removedMachineImages = sets.Set[string]{} - removedMachineImageVersions = map[string]sets.Set[string]{} - addedMachineImages = sets.Set[string]{} - addedMachineImageVersions = map[string]sets.Set[string]{} +func GetMachineImageDiff(old, new []core.MachineImage) MachineImageDiff { + diff := MachineImageDiff{ + RemovedImages: sets.Set[string]{}, + RemovedVersions: map[string]sets.Set[string]{}, + RemovedVersionClassifications: map[string]map[string][]core.VersionClassification{}, + AddedImages: sets.Set[string]{}, + AddedVersions: map[string]sets.Set[string]{}, + } oldImages := utils.CreateMapFromSlice(old, func(image core.MachineImage) string { return image.Name }) newImages := utils.CreateMapFromSlice(new, func(image core.MachineImage) string { return image.Name }) @@ -334,8 +346,8 @@ func GetMachineImageDiff(old, new []core.MachineImage) (removedMachineImages set newImage, exists := newImages[imageName] if !exists { // Completely removed images. - removedMachineImages.Insert(imageName) - removedMachineImageVersions[imageName] = oldImageVersionsSet + diff.RemovedImages.Insert(imageName) + diff.RemovedVersions[imageName] = oldImageVersionsSet } else { // Check for image versions diff. newImageVersions := utils.CreateMapFromSlice(newImage.Versions, func(version core.MachineImageVersion) string { return version.Version }) @@ -343,11 +355,30 @@ func GetMachineImageDiff(old, new []core.MachineImage) (removedMachineImages set removedDiff := oldImageVersionsSet.Difference(newImageVersionsSet) if removedDiff.Len() > 0 { - removedMachineImageVersions[imageName] = removedDiff + diff.RemovedVersions[imageName] = removedDiff } addedDiff := newImageVersionsSet.Difference(oldImageVersionsSet) if addedDiff.Len() > 0 { - addedMachineImageVersions[imageName] = addedDiff + diff.AddedVersions[imageName] = addedDiff + } + + for _, version := range oldImageVersions { + if removedDiff.Has(version.Version) { + continue + } + for _, existingStage := range version.Lifecycle { + if slices.ContainsFunc(newImageVersions[version.Version].Lifecycle, func(newStage core.LifecycleStage) bool { + return newStage.Classification == existingStage.Classification + }) { + continue + } + removedClassifications := diff.RemovedVersionClassifications[imageName] + if removedClassifications == nil { + removedClassifications = make(map[string][]core.VersionClassification) + diff.RemovedVersionClassifications[imageName] = removedClassifications + } + removedClassifications[version.Version] = append(removedClassifications[version.Version], existingStage.Classification) + } } } } @@ -358,18 +389,21 @@ func GetMachineImageDiff(old, new []core.MachineImage) (removedMachineImages set newImageVersions := utils.CreateMapFromSlice(newImage.Versions, func(version core.MachineImageVersion) string { return version.Version }) newImageVersionsSet := sets.KeySet(newImageVersions) - addedMachineImages.Insert(imageName) - addedMachineImageVersions[imageName] = newImageVersionsSet + diff.AddedImages.Insert(imageName) + diff.AddedVersions[imageName] = newImageVersionsSet } } - return + return diff } // FilterVersionsWithClassification filters versions for a classification func FilterVersionsWithClassification(versions []core.ExpirableVersion, classification core.VersionClassification) []core.ExpirableVersion { var result []core.ExpirableVersion for _, version := range versions { - if version.Classification == nil || *version.Classification != classification { + if (version.Classification == nil || *version.Classification != classification) && + !slices.ContainsFunc(version.Lifecycle, func(s core.LifecycleStage) bool { + return s.Classification == classification + }) { continue } diff --git a/pkg/apis/core/helper/helpers_test.go b/pkg/apis/core/helper/helpers_test.go index c62a8407246..868314e4945 100644 --- a/pkg/apis/core/helper/helpers_test.go +++ b/pkg/apis/core/helper/helpers_test.go @@ -1147,17 +1147,17 @@ var _ = Describe("helper", func() { }, } - removedImages, removedVersions, addedImages, addedVersions := GetMachineImageDiff(versions1, versions2) + diff := GetMachineImageDiff(versions1, versions2) - Expect(removedImages.UnsortedList()).To(ConsistOf("image-1")) - Expect(removedVersions).To(BeEquivalentTo( + Expect(diff.RemovedImages.UnsortedList()).To(ConsistOf("image-1")) + Expect(diff.RemovedVersions).To(BeEquivalentTo( map[string]sets.Set[string]{ "image-1": sets.New[string]("version-1", "version-2"), "image-2": sets.New[string]("version-1"), }, )) - Expect(addedImages.UnsortedList()).To(ConsistOf("image-3")) - Expect(addedVersions).To(BeEquivalentTo( + Expect(diff.AddedImages.UnsortedList()).To(ConsistOf("image-3")) + Expect(diff.AddedVersions).To(BeEquivalentTo( map[string]sets.Set[string]{ "image-2": sets.New[string]("version-3"), "image-3": sets.New[string]("version-1", "version-2"), @@ -1182,12 +1182,12 @@ var _ = Describe("helper", func() { }, } - removedImages, removedVersions, addedImages, addedVersions := GetMachineImageDiff(nil, versions2) + diff := GetMachineImageDiff(nil, versions2) - Expect(removedImages.UnsortedList()).To(BeEmpty()) - Expect(removedVersions).To(BeEmpty()) - Expect(addedImages.UnsortedList()).To(ConsistOf("image-2", "image-3")) - Expect(addedVersions).To(BeEquivalentTo( + Expect(diff.RemovedImages.UnsortedList()).To(BeEmpty()) + Expect(diff.RemovedVersions).To(BeEmpty()) + Expect(diff.AddedImages.UnsortedList()).To(ConsistOf("image-2", "image-3")) + Expect(diff.AddedVersions).To(BeEquivalentTo( map[string]sets.Set[string]{ "image-2": sets.New[string]("version-3"), "image-3": sets.New[string]("version-1", "version-2"), @@ -1212,26 +1212,26 @@ var _ = Describe("helper", func() { }, } - removedImages, removedVersions, addedImages, addedVersions := GetMachineImageDiff(versions1, []core.MachineImage{}) + diff := GetMachineImageDiff(versions1, []core.MachineImage{}) - Expect(removedImages.UnsortedList()).To(ConsistOf("image-2", "image-3")) - Expect(removedVersions).To(BeEquivalentTo( + Expect(diff.RemovedImages.UnsortedList()).To(ConsistOf("image-2", "image-3")) + Expect(diff.RemovedVersions).To(BeEquivalentTo( map[string]sets.Set[string]{ "image-2": sets.New[string]("version-3"), "image-3": sets.New[string]("version-1", "version-2"), }, )) - Expect(addedImages.UnsortedList()).To(BeEmpty()) - Expect(addedVersions).To(BeEmpty()) + Expect(diff.AddedImages.UnsortedList()).To(BeEmpty()) + Expect(diff.AddedVersions).To(BeEmpty()) }) It("should return the diff between two empty machine image slices", func() { - removedImages, removedVersions, addedImages, addedVersions := GetMachineImageDiff([]core.MachineImage{}, nil) + diff := GetMachineImageDiff([]core.MachineImage{}, nil) - Expect(removedImages.UnsortedList()).To(BeEmpty()) - Expect(removedVersions).To(BeEmpty()) - Expect(addedImages.UnsortedList()).To(BeEmpty()) - Expect(addedVersions).To(BeEmpty()) + Expect(diff.RemovedImages.UnsortedList()).To(BeEmpty()) + Expect(diff.RemovedVersions).To(BeEmpty()) + Expect(diff.AddedImages.UnsortedList()).To(BeEmpty()) + Expect(diff.AddedVersions).To(BeEmpty()) }) }) }) diff --git a/pkg/apis/core/types_cloudprofile.go b/pkg/apis/core/types_cloudprofile.go index fee02a77b31..a0d14f8344d 100644 --- a/pkg/apis/core/types_cloudprofile.go +++ b/pkg/apis/core/types_cloudprofile.go @@ -21,6 +21,8 @@ type CloudProfile struct { metav1.ObjectMeta // Spec defines the provider environment properties. Spec CloudProfileSpec + // Status contains the current status of the cloud profile. + Status CloudProfileStatus } // +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object @@ -118,10 +120,20 @@ type MachineImageVersion struct { type ExpirableVersion struct { // Version is the version identifier. Version string - // ExpirationDate defines the time at which this version expires. + // Deprecated: Is replaced by Lifecycle. ExpirationDate *metav1.Time - // Classification defines the state of a version (preview, supported, deprecated) + // Classification defines the state of a version (preview, supported, deprecated). + // Deprecated: Is replaced by Lifecycle. Classification *VersionClassification + // Lifecycle defines the lifecycle stages for this version. Cannot be used in combination with deprecated Classification and ExpirationDate. + Lifecycle []LifecycleStage +} + +type LifecycleStage struct { + // Classification is the category of this lifecycle stage (unavailable, preview, supported, deprecated, expired). + Classification VersionClassification + // StartTime defines when this lifecycle stage becomes active. + StartTime *metav1.Time } // MachineType contains certain properties of a machine type. @@ -213,6 +225,29 @@ type BastionMachineType struct { Name string } +// CloudProfileStatus contains the status of the cloud profile. +type CloudProfileStatus struct { + // KubernetesVersions contains the statuses of the kubernetes versions. + KubernetesVersions []ExpirableVersionStatus + // MachineImageVersions contains the statuses of the machine image versions. + MachineImageVersions []MachineImageVersionStatus +} + +type MachineImageVersionStatus struct { + // Name matches the name of the MachineImage the status is represented of. + Name string + // Versions contains the statuses of the machine image versions. + Versions []ExpirableVersionStatus +} + +// ExpirableVersionStatus defines the current status of an expirable version. +type ExpirableVersionStatus struct { + // Version is the version identifier. + Version string `json:"version" protobuf:"bytes,1,opt,name=version"` + // ClassificationState reflects the current state in the classification lifecycle. + ClassificationState VersionClassification `json:"classificationState,omitempty" protobuf:"bytes,2,opt,name=classificationState,casttype=VersionClassification"` +} + const ( // VolumeClassStandard is a constant for the standard volume class. VolumeClassStandard string = "standard" @@ -223,7 +258,21 @@ const ( // VersionClassification is the logical state of a version. type VersionClassification string +var order = map[VersionClassification]int{ + ClassificationUnavailable: 0, + ClassificationPreview: 1, + ClassificationSupported: 2, + ClassificationDeprecated: 3, + ClassificationExpired: 4, +} + +func (c1 VersionClassification) Compare(c2 VersionClassification) int { + return order[c1] - order[c2] +} + const ( + // ClassificationUnavailable indicates that a version is currently not available and is planned to become available depending on the classification lifecycle. + ClassificationUnavailable VersionClassification = "unavailable" // ClassificationPreview indicates that a version has recently been added and not promoted to "Supported" yet. // ClassificationPreview versions will not be considered for automatic Kubernetes and Machine Image patch version updates. ClassificationPreview VersionClassification = "preview" @@ -234,6 +283,9 @@ const ( // ClassificationDeprecated indicates that a patch version should not be used anymore, should be updated to a new version // and will eventually expire. ClassificationDeprecated VersionClassification = "deprecated" + // ClassificationExpired indicates that a version has expired. + // New entities with that version cannot be created and existing entities are forcefully migrated to a higher version during the maintenance time. + ClassificationExpired VersionClassification = "expired" ) // MachineImageUpdateStrategy is the update strategy to use for a machine image diff --git a/pkg/apis/core/v1beta1/generated.pb.go b/pkg/apis/core/v1beta1/generated.pb.go index f9f52e1641f..63772fa0537 100644 --- a/pkg/apis/core/v1beta1/generated.pb.go +++ b/pkg/apis/core/v1beta1/generated.pb.go @@ -883,10 +883,38 @@ func (m *CloudProfileSpec) XXX_DiscardUnknown() { var xxx_messageInfo_CloudProfileSpec proto.InternalMessageInfo +func (m *CloudProfileStatus) Reset() { *m = CloudProfileStatus{} } +func (*CloudProfileStatus) ProtoMessage() {} +func (*CloudProfileStatus) Descriptor() ([]byte, []int) { + return fileDescriptor_ca37af0df9a5bbd2, []int{30} +} +func (m *CloudProfileStatus) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *CloudProfileStatus) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil +} +func (m *CloudProfileStatus) XXX_Merge(src proto.Message) { + xxx_messageInfo_CloudProfileStatus.Merge(m, src) +} +func (m *CloudProfileStatus) XXX_Size() int { + return m.Size() +} +func (m *CloudProfileStatus) XXX_DiscardUnknown() { + xxx_messageInfo_CloudProfileStatus.DiscardUnknown(m) +} + +var xxx_messageInfo_CloudProfileStatus proto.InternalMessageInfo + func (m *ClusterAutoscaler) Reset() { *m = ClusterAutoscaler{} } func (*ClusterAutoscaler) ProtoMessage() {} func (*ClusterAutoscaler) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{30} + return fileDescriptor_ca37af0df9a5bbd2, []int{31} } func (m *ClusterAutoscaler) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -914,7 +942,7 @@ var xxx_messageInfo_ClusterAutoscaler proto.InternalMessageInfo func (m *ClusterAutoscalerOptions) Reset() { *m = ClusterAutoscalerOptions{} } func (*ClusterAutoscalerOptions) ProtoMessage() {} func (*ClusterAutoscalerOptions) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{31} + return fileDescriptor_ca37af0df9a5bbd2, []int{32} } func (m *ClusterAutoscalerOptions) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -942,7 +970,7 @@ var xxx_messageInfo_ClusterAutoscalerOptions proto.InternalMessageInfo func (m *Condition) Reset() { *m = Condition{} } func (*Condition) ProtoMessage() {} func (*Condition) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{32} + return fileDescriptor_ca37af0df9a5bbd2, []int{33} } func (m *Condition) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -970,7 +998,7 @@ var xxx_messageInfo_Condition proto.InternalMessageInfo func (m *ContainerRuntime) Reset() { *m = ContainerRuntime{} } func (*ContainerRuntime) ProtoMessage() {} func (*ContainerRuntime) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{33} + return fileDescriptor_ca37af0df9a5bbd2, []int{34} } func (m *ContainerRuntime) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -998,7 +1026,7 @@ var xxx_messageInfo_ContainerRuntime proto.InternalMessageInfo func (m *ControlPlane) Reset() { *m = ControlPlane{} } func (*ControlPlane) ProtoMessage() {} func (*ControlPlane) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{34} + return fileDescriptor_ca37af0df9a5bbd2, []int{35} } func (m *ControlPlane) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1026,7 +1054,7 @@ var xxx_messageInfo_ControlPlane proto.InternalMessageInfo func (m *ControllerDeployment) Reset() { *m = ControllerDeployment{} } func (*ControllerDeployment) ProtoMessage() {} func (*ControllerDeployment) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{35} + return fileDescriptor_ca37af0df9a5bbd2, []int{36} } func (m *ControllerDeployment) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1054,7 +1082,7 @@ var xxx_messageInfo_ControllerDeployment proto.InternalMessageInfo func (m *ControllerDeploymentList) Reset() { *m = ControllerDeploymentList{} } func (*ControllerDeploymentList) ProtoMessage() {} func (*ControllerDeploymentList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{36} + return fileDescriptor_ca37af0df9a5bbd2, []int{37} } func (m *ControllerDeploymentList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1082,7 +1110,7 @@ var xxx_messageInfo_ControllerDeploymentList proto.InternalMessageInfo func (m *ControllerInstallation) Reset() { *m = ControllerInstallation{} } func (*ControllerInstallation) ProtoMessage() {} func (*ControllerInstallation) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{37} + return fileDescriptor_ca37af0df9a5bbd2, []int{38} } func (m *ControllerInstallation) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1110,7 +1138,7 @@ var xxx_messageInfo_ControllerInstallation proto.InternalMessageInfo func (m *ControllerInstallationList) Reset() { *m = ControllerInstallationList{} } func (*ControllerInstallationList) ProtoMessage() {} func (*ControllerInstallationList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{38} + return fileDescriptor_ca37af0df9a5bbd2, []int{39} } func (m *ControllerInstallationList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1138,7 +1166,7 @@ var xxx_messageInfo_ControllerInstallationList proto.InternalMessageInfo func (m *ControllerInstallationSpec) Reset() { *m = ControllerInstallationSpec{} } func (*ControllerInstallationSpec) ProtoMessage() {} func (*ControllerInstallationSpec) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{39} + return fileDescriptor_ca37af0df9a5bbd2, []int{40} } func (m *ControllerInstallationSpec) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1166,7 +1194,7 @@ var xxx_messageInfo_ControllerInstallationSpec proto.InternalMessageInfo func (m *ControllerInstallationStatus) Reset() { *m = ControllerInstallationStatus{} } func (*ControllerInstallationStatus) ProtoMessage() {} func (*ControllerInstallationStatus) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{40} + return fileDescriptor_ca37af0df9a5bbd2, []int{41} } func (m *ControllerInstallationStatus) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1194,7 +1222,7 @@ var xxx_messageInfo_ControllerInstallationStatus proto.InternalMessageInfo func (m *ControllerRegistration) Reset() { *m = ControllerRegistration{} } func (*ControllerRegistration) ProtoMessage() {} func (*ControllerRegistration) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{41} + return fileDescriptor_ca37af0df9a5bbd2, []int{42} } func (m *ControllerRegistration) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1222,7 +1250,7 @@ var xxx_messageInfo_ControllerRegistration proto.InternalMessageInfo func (m *ControllerRegistrationDeployment) Reset() { *m = ControllerRegistrationDeployment{} } func (*ControllerRegistrationDeployment) ProtoMessage() {} func (*ControllerRegistrationDeployment) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{42} + return fileDescriptor_ca37af0df9a5bbd2, []int{43} } func (m *ControllerRegistrationDeployment) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1250,7 +1278,7 @@ var xxx_messageInfo_ControllerRegistrationDeployment proto.InternalMessageInfo func (m *ControllerRegistrationList) Reset() { *m = ControllerRegistrationList{} } func (*ControllerRegistrationList) ProtoMessage() {} func (*ControllerRegistrationList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{43} + return fileDescriptor_ca37af0df9a5bbd2, []int{44} } func (m *ControllerRegistrationList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1278,7 +1306,7 @@ var xxx_messageInfo_ControllerRegistrationList proto.InternalMessageInfo func (m *ControllerRegistrationSpec) Reset() { *m = ControllerRegistrationSpec{} } func (*ControllerRegistrationSpec) ProtoMessage() {} func (*ControllerRegistrationSpec) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{44} + return fileDescriptor_ca37af0df9a5bbd2, []int{45} } func (m *ControllerRegistrationSpec) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1306,7 +1334,7 @@ var xxx_messageInfo_ControllerRegistrationSpec proto.InternalMessageInfo func (m *ControllerResource) Reset() { *m = ControllerResource{} } func (*ControllerResource) ProtoMessage() {} func (*ControllerResource) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{45} + return fileDescriptor_ca37af0df9a5bbd2, []int{46} } func (m *ControllerResource) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1334,7 +1362,7 @@ var xxx_messageInfo_ControllerResource proto.InternalMessageInfo func (m *ControllerResourceLifecycle) Reset() { *m = ControllerResourceLifecycle{} } func (*ControllerResourceLifecycle) ProtoMessage() {} func (*ControllerResourceLifecycle) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{46} + return fileDescriptor_ca37af0df9a5bbd2, []int{47} } func (m *ControllerResourceLifecycle) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1362,7 +1390,7 @@ var xxx_messageInfo_ControllerResourceLifecycle proto.InternalMessageInfo func (m *CoreDNS) Reset() { *m = CoreDNS{} } func (*CoreDNS) ProtoMessage() {} func (*CoreDNS) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{47} + return fileDescriptor_ca37af0df9a5bbd2, []int{48} } func (m *CoreDNS) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1390,7 +1418,7 @@ var xxx_messageInfo_CoreDNS proto.InternalMessageInfo func (m *CoreDNSAutoscaling) Reset() { *m = CoreDNSAutoscaling{} } func (*CoreDNSAutoscaling) ProtoMessage() {} func (*CoreDNSAutoscaling) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{48} + return fileDescriptor_ca37af0df9a5bbd2, []int{49} } func (m *CoreDNSAutoscaling) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1418,7 +1446,7 @@ var xxx_messageInfo_CoreDNSAutoscaling proto.InternalMessageInfo func (m *CoreDNSRewriting) Reset() { *m = CoreDNSRewriting{} } func (*CoreDNSRewriting) ProtoMessage() {} func (*CoreDNSRewriting) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{49} + return fileDescriptor_ca37af0df9a5bbd2, []int{50} } func (m *CoreDNSRewriting) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1446,7 +1474,7 @@ var xxx_messageInfo_CoreDNSRewriting proto.InternalMessageInfo func (m *DNS) Reset() { *m = DNS{} } func (*DNS) ProtoMessage() {} func (*DNS) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{50} + return fileDescriptor_ca37af0df9a5bbd2, []int{51} } func (m *DNS) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1474,7 +1502,7 @@ var xxx_messageInfo_DNS proto.InternalMessageInfo func (m *DNSIncludeExclude) Reset() { *m = DNSIncludeExclude{} } func (*DNSIncludeExclude) ProtoMessage() {} func (*DNSIncludeExclude) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{51} + return fileDescriptor_ca37af0df9a5bbd2, []int{52} } func (m *DNSIncludeExclude) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1502,7 +1530,7 @@ var xxx_messageInfo_DNSIncludeExclude proto.InternalMessageInfo func (m *DNSProvider) Reset() { *m = DNSProvider{} } func (*DNSProvider) ProtoMessage() {} func (*DNSProvider) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{52} + return fileDescriptor_ca37af0df9a5bbd2, []int{53} } func (m *DNSProvider) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1530,7 +1558,7 @@ var xxx_messageInfo_DNSProvider proto.InternalMessageInfo func (m *DataVolume) Reset() { *m = DataVolume{} } func (*DataVolume) ProtoMessage() {} func (*DataVolume) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{53} + return fileDescriptor_ca37af0df9a5bbd2, []int{54} } func (m *DataVolume) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1558,7 +1586,7 @@ var xxx_messageInfo_DataVolume proto.InternalMessageInfo func (m *DeploymentRef) Reset() { *m = DeploymentRef{} } func (*DeploymentRef) ProtoMessage() {} func (*DeploymentRef) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{54} + return fileDescriptor_ca37af0df9a5bbd2, []int{55} } func (m *DeploymentRef) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1586,7 +1614,7 @@ var xxx_messageInfo_DeploymentRef proto.InternalMessageInfo func (m *DualApprovalForDeletion) Reset() { *m = DualApprovalForDeletion{} } func (*DualApprovalForDeletion) ProtoMessage() {} func (*DualApprovalForDeletion) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{55} + return fileDescriptor_ca37af0df9a5bbd2, []int{56} } func (m *DualApprovalForDeletion) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1614,7 +1642,7 @@ var xxx_messageInfo_DualApprovalForDeletion proto.InternalMessageInfo func (m *ETCDEncryptionKeyRotation) Reset() { *m = ETCDEncryptionKeyRotation{} } func (*ETCDEncryptionKeyRotation) ProtoMessage() {} func (*ETCDEncryptionKeyRotation) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{56} + return fileDescriptor_ca37af0df9a5bbd2, []int{57} } func (m *ETCDEncryptionKeyRotation) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1642,7 +1670,7 @@ var xxx_messageInfo_ETCDEncryptionKeyRotation proto.InternalMessageInfo func (m *EncryptionConfig) Reset() { *m = EncryptionConfig{} } func (*EncryptionConfig) ProtoMessage() {} func (*EncryptionConfig) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{57} + return fileDescriptor_ca37af0df9a5bbd2, []int{58} } func (m *EncryptionConfig) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1670,7 +1698,7 @@ var xxx_messageInfo_EncryptionConfig proto.InternalMessageInfo func (m *ExpirableVersion) Reset() { *m = ExpirableVersion{} } func (*ExpirableVersion) ProtoMessage() {} func (*ExpirableVersion) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{58} + return fileDescriptor_ca37af0df9a5bbd2, []int{59} } func (m *ExpirableVersion) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1695,10 +1723,38 @@ func (m *ExpirableVersion) XXX_DiscardUnknown() { var xxx_messageInfo_ExpirableVersion proto.InternalMessageInfo +func (m *ExpirableVersionStatus) Reset() { *m = ExpirableVersionStatus{} } +func (*ExpirableVersionStatus) ProtoMessage() {} +func (*ExpirableVersionStatus) Descriptor() ([]byte, []int) { + return fileDescriptor_ca37af0df9a5bbd2, []int{60} +} +func (m *ExpirableVersionStatus) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *ExpirableVersionStatus) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil +} +func (m *ExpirableVersionStatus) XXX_Merge(src proto.Message) { + xxx_messageInfo_ExpirableVersionStatus.Merge(m, src) +} +func (m *ExpirableVersionStatus) XXX_Size() int { + return m.Size() +} +func (m *ExpirableVersionStatus) XXX_DiscardUnknown() { + xxx_messageInfo_ExpirableVersionStatus.DiscardUnknown(m) +} + +var xxx_messageInfo_ExpirableVersionStatus proto.InternalMessageInfo + func (m *ExposureClass) Reset() { *m = ExposureClass{} } func (*ExposureClass) ProtoMessage() {} func (*ExposureClass) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{59} + return fileDescriptor_ca37af0df9a5bbd2, []int{61} } func (m *ExposureClass) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1726,7 +1782,7 @@ var xxx_messageInfo_ExposureClass proto.InternalMessageInfo func (m *ExposureClassList) Reset() { *m = ExposureClassList{} } func (*ExposureClassList) ProtoMessage() {} func (*ExposureClassList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{60} + return fileDescriptor_ca37af0df9a5bbd2, []int{62} } func (m *ExposureClassList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1754,7 +1810,7 @@ var xxx_messageInfo_ExposureClassList proto.InternalMessageInfo func (m *ExposureClassScheduling) Reset() { *m = ExposureClassScheduling{} } func (*ExposureClassScheduling) ProtoMessage() {} func (*ExposureClassScheduling) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{61} + return fileDescriptor_ca37af0df9a5bbd2, []int{63} } func (m *ExposureClassScheduling) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1782,7 +1838,7 @@ var xxx_messageInfo_ExposureClassScheduling proto.InternalMessageInfo func (m *Extension) Reset() { *m = Extension{} } func (*Extension) ProtoMessage() {} func (*Extension) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{62} + return fileDescriptor_ca37af0df9a5bbd2, []int{64} } func (m *Extension) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1810,7 +1866,7 @@ var xxx_messageInfo_Extension proto.InternalMessageInfo func (m *ExtensionResourceState) Reset() { *m = ExtensionResourceState{} } func (*ExtensionResourceState) ProtoMessage() {} func (*ExtensionResourceState) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{63} + return fileDescriptor_ca37af0df9a5bbd2, []int{65} } func (m *ExtensionResourceState) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1838,7 +1894,7 @@ var xxx_messageInfo_ExtensionResourceState proto.InternalMessageInfo func (m *FailureTolerance) Reset() { *m = FailureTolerance{} } func (*FailureTolerance) ProtoMessage() {} func (*FailureTolerance) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{64} + return fileDescriptor_ca37af0df9a5bbd2, []int{66} } func (m *FailureTolerance) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1866,7 +1922,7 @@ var xxx_messageInfo_FailureTolerance proto.InternalMessageInfo func (m *Gardener) Reset() { *m = Gardener{} } func (*Gardener) ProtoMessage() {} func (*Gardener) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{65} + return fileDescriptor_ca37af0df9a5bbd2, []int{67} } func (m *Gardener) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1894,7 +1950,7 @@ var xxx_messageInfo_Gardener proto.InternalMessageInfo func (m *GardenerResourceData) Reset() { *m = GardenerResourceData{} } func (*GardenerResourceData) ProtoMessage() {} func (*GardenerResourceData) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{66} + return fileDescriptor_ca37af0df9a5bbd2, []int{68} } func (m *GardenerResourceData) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1922,7 +1978,7 @@ var xxx_messageInfo_GardenerResourceData proto.InternalMessageInfo func (m *HelmControllerDeployment) Reset() { *m = HelmControllerDeployment{} } func (*HelmControllerDeployment) ProtoMessage() {} func (*HelmControllerDeployment) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{67} + return fileDescriptor_ca37af0df9a5bbd2, []int{69} } func (m *HelmControllerDeployment) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1950,7 +2006,7 @@ var xxx_messageInfo_HelmControllerDeployment proto.InternalMessageInfo func (m *Hibernation) Reset() { *m = Hibernation{} } func (*Hibernation) ProtoMessage() {} func (*Hibernation) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{68} + return fileDescriptor_ca37af0df9a5bbd2, []int{70} } func (m *Hibernation) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -1978,7 +2034,7 @@ var xxx_messageInfo_Hibernation proto.InternalMessageInfo func (m *HibernationSchedule) Reset() { *m = HibernationSchedule{} } func (*HibernationSchedule) ProtoMessage() {} func (*HibernationSchedule) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{69} + return fileDescriptor_ca37af0df9a5bbd2, []int{71} } func (m *HibernationSchedule) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2006,7 +2062,7 @@ var xxx_messageInfo_HibernationSchedule proto.InternalMessageInfo func (m *HighAvailability) Reset() { *m = HighAvailability{} } func (*HighAvailability) ProtoMessage() {} func (*HighAvailability) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{70} + return fileDescriptor_ca37af0df9a5bbd2, []int{72} } func (m *HighAvailability) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2034,7 +2090,7 @@ var xxx_messageInfo_HighAvailability proto.InternalMessageInfo func (m *HorizontalPodAutoscalerConfig) Reset() { *m = HorizontalPodAutoscalerConfig{} } func (*HorizontalPodAutoscalerConfig) ProtoMessage() {} func (*HorizontalPodAutoscalerConfig) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{71} + return fileDescriptor_ca37af0df9a5bbd2, []int{73} } func (m *HorizontalPodAutoscalerConfig) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2062,7 +2118,7 @@ var xxx_messageInfo_HorizontalPodAutoscalerConfig proto.InternalMessageInfo func (m *Ingress) Reset() { *m = Ingress{} } func (*Ingress) ProtoMessage() {} func (*Ingress) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{72} + return fileDescriptor_ca37af0df9a5bbd2, []int{74} } func (m *Ingress) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2090,7 +2146,7 @@ var xxx_messageInfo_Ingress proto.InternalMessageInfo func (m *IngressController) Reset() { *m = IngressController{} } func (*IngressController) ProtoMessage() {} func (*IngressController) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{73} + return fileDescriptor_ca37af0df9a5bbd2, []int{75} } func (m *IngressController) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2118,7 +2174,7 @@ var xxx_messageInfo_IngressController proto.InternalMessageInfo func (m *InternalSecret) Reset() { *m = InternalSecret{} } func (*InternalSecret) ProtoMessage() {} func (*InternalSecret) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{74} + return fileDescriptor_ca37af0df9a5bbd2, []int{76} } func (m *InternalSecret) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2146,7 +2202,7 @@ var xxx_messageInfo_InternalSecret proto.InternalMessageInfo func (m *InternalSecretList) Reset() { *m = InternalSecretList{} } func (*InternalSecretList) ProtoMessage() {} func (*InternalSecretList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{75} + return fileDescriptor_ca37af0df9a5bbd2, []int{77} } func (m *InternalSecretList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2174,7 +2230,7 @@ var xxx_messageInfo_InternalSecretList proto.InternalMessageInfo func (m *KubeAPIServerConfig) Reset() { *m = KubeAPIServerConfig{} } func (*KubeAPIServerConfig) ProtoMessage() {} func (*KubeAPIServerConfig) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{76} + return fileDescriptor_ca37af0df9a5bbd2, []int{78} } func (m *KubeAPIServerConfig) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2202,7 +2258,7 @@ var xxx_messageInfo_KubeAPIServerConfig proto.InternalMessageInfo func (m *KubeControllerManagerConfig) Reset() { *m = KubeControllerManagerConfig{} } func (*KubeControllerManagerConfig) ProtoMessage() {} func (*KubeControllerManagerConfig) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{77} + return fileDescriptor_ca37af0df9a5bbd2, []int{79} } func (m *KubeControllerManagerConfig) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2230,7 +2286,7 @@ var xxx_messageInfo_KubeControllerManagerConfig proto.InternalMessageInfo func (m *KubeProxyConfig) Reset() { *m = KubeProxyConfig{} } func (*KubeProxyConfig) ProtoMessage() {} func (*KubeProxyConfig) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{78} + return fileDescriptor_ca37af0df9a5bbd2, []int{80} } func (m *KubeProxyConfig) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2258,7 +2314,7 @@ var xxx_messageInfo_KubeProxyConfig proto.InternalMessageInfo func (m *KubeSchedulerConfig) Reset() { *m = KubeSchedulerConfig{} } func (*KubeSchedulerConfig) ProtoMessage() {} func (*KubeSchedulerConfig) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{79} + return fileDescriptor_ca37af0df9a5bbd2, []int{81} } func (m *KubeSchedulerConfig) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2286,7 +2342,7 @@ var xxx_messageInfo_KubeSchedulerConfig proto.InternalMessageInfo func (m *KubeletConfig) Reset() { *m = KubeletConfig{} } func (*KubeletConfig) ProtoMessage() {} func (*KubeletConfig) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{80} + return fileDescriptor_ca37af0df9a5bbd2, []int{82} } func (m *KubeletConfig) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2314,7 +2370,7 @@ var xxx_messageInfo_KubeletConfig proto.InternalMessageInfo func (m *KubeletConfigEviction) Reset() { *m = KubeletConfigEviction{} } func (*KubeletConfigEviction) ProtoMessage() {} func (*KubeletConfigEviction) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{81} + return fileDescriptor_ca37af0df9a5bbd2, []int{83} } func (m *KubeletConfigEviction) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2342,7 +2398,7 @@ var xxx_messageInfo_KubeletConfigEviction proto.InternalMessageInfo func (m *KubeletConfigEvictionMinimumReclaim) Reset() { *m = KubeletConfigEvictionMinimumReclaim{} } func (*KubeletConfigEvictionMinimumReclaim) ProtoMessage() {} func (*KubeletConfigEvictionMinimumReclaim) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{82} + return fileDescriptor_ca37af0df9a5bbd2, []int{84} } func (m *KubeletConfigEvictionMinimumReclaim) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2370,7 +2426,7 @@ var xxx_messageInfo_KubeletConfigEvictionMinimumReclaim proto.InternalMessageInf func (m *KubeletConfigEvictionSoftGracePeriod) Reset() { *m = KubeletConfigEvictionSoftGracePeriod{} } func (*KubeletConfigEvictionSoftGracePeriod) ProtoMessage() {} func (*KubeletConfigEvictionSoftGracePeriod) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{83} + return fileDescriptor_ca37af0df9a5bbd2, []int{85} } func (m *KubeletConfigEvictionSoftGracePeriod) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2398,7 +2454,7 @@ var xxx_messageInfo_KubeletConfigEvictionSoftGracePeriod proto.InternalMessageIn func (m *KubeletConfigReserved) Reset() { *m = KubeletConfigReserved{} } func (*KubeletConfigReserved) ProtoMessage() {} func (*KubeletConfigReserved) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{84} + return fileDescriptor_ca37af0df9a5bbd2, []int{86} } func (m *KubeletConfigReserved) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2426,7 +2482,7 @@ var xxx_messageInfo_KubeletConfigReserved proto.InternalMessageInfo func (m *Kubernetes) Reset() { *m = Kubernetes{} } func (*Kubernetes) ProtoMessage() {} func (*Kubernetes) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{85} + return fileDescriptor_ca37af0df9a5bbd2, []int{87} } func (m *Kubernetes) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2454,7 +2510,7 @@ var xxx_messageInfo_Kubernetes proto.InternalMessageInfo func (m *KubernetesConfig) Reset() { *m = KubernetesConfig{} } func (*KubernetesConfig) ProtoMessage() {} func (*KubernetesConfig) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{86} + return fileDescriptor_ca37af0df9a5bbd2, []int{88} } func (m *KubernetesConfig) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2482,7 +2538,7 @@ var xxx_messageInfo_KubernetesConfig proto.InternalMessageInfo func (m *KubernetesDashboard) Reset() { *m = KubernetesDashboard{} } func (*KubernetesDashboard) ProtoMessage() {} func (*KubernetesDashboard) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{87} + return fileDescriptor_ca37af0df9a5bbd2, []int{89} } func (m *KubernetesDashboard) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2510,7 +2566,7 @@ var xxx_messageInfo_KubernetesDashboard proto.InternalMessageInfo func (m *KubernetesSettings) Reset() { *m = KubernetesSettings{} } func (*KubernetesSettings) ProtoMessage() {} func (*KubernetesSettings) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{88} + return fileDescriptor_ca37af0df9a5bbd2, []int{90} } func (m *KubernetesSettings) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2538,7 +2594,7 @@ var xxx_messageInfo_KubernetesSettings proto.InternalMessageInfo func (m *LastError) Reset() { *m = LastError{} } func (*LastError) ProtoMessage() {} func (*LastError) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{89} + return fileDescriptor_ca37af0df9a5bbd2, []int{91} } func (m *LastError) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2566,7 +2622,7 @@ var xxx_messageInfo_LastError proto.InternalMessageInfo func (m *LastMaintenance) Reset() { *m = LastMaintenance{} } func (*LastMaintenance) ProtoMessage() {} func (*LastMaintenance) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{90} + return fileDescriptor_ca37af0df9a5bbd2, []int{92} } func (m *LastMaintenance) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2594,7 +2650,7 @@ var xxx_messageInfo_LastMaintenance proto.InternalMessageInfo func (m *LastOperation) Reset() { *m = LastOperation{} } func (*LastOperation) ProtoMessage() {} func (*LastOperation) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{91} + return fileDescriptor_ca37af0df9a5bbd2, []int{93} } func (m *LastOperation) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2619,10 +2675,38 @@ func (m *LastOperation) XXX_DiscardUnknown() { var xxx_messageInfo_LastOperation proto.InternalMessageInfo +func (m *LifecycleStage) Reset() { *m = LifecycleStage{} } +func (*LifecycleStage) ProtoMessage() {} +func (*LifecycleStage) Descriptor() ([]byte, []int) { + return fileDescriptor_ca37af0df9a5bbd2, []int{94} +} +func (m *LifecycleStage) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *LifecycleStage) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil +} +func (m *LifecycleStage) XXX_Merge(src proto.Message) { + xxx_messageInfo_LifecycleStage.Merge(m, src) +} +func (m *LifecycleStage) XXX_Size() int { + return m.Size() +} +func (m *LifecycleStage) XXX_DiscardUnknown() { + xxx_messageInfo_LifecycleStage.DiscardUnknown(m) +} + +var xxx_messageInfo_LifecycleStage proto.InternalMessageInfo + func (m *LoadBalancerServicesProxyProtocol) Reset() { *m = LoadBalancerServicesProxyProtocol{} } func (*LoadBalancerServicesProxyProtocol) ProtoMessage() {} func (*LoadBalancerServicesProxyProtocol) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{92} + return fileDescriptor_ca37af0df9a5bbd2, []int{95} } func (m *LoadBalancerServicesProxyProtocol) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2650,7 +2734,7 @@ var xxx_messageInfo_LoadBalancerServicesProxyProtocol proto.InternalMessageInfo func (m *Machine) Reset() { *m = Machine{} } func (*Machine) ProtoMessage() {} func (*Machine) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{93} + return fileDescriptor_ca37af0df9a5bbd2, []int{96} } func (m *Machine) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2678,7 +2762,7 @@ var xxx_messageInfo_Machine proto.InternalMessageInfo func (m *MachineControllerManagerSettings) Reset() { *m = MachineControllerManagerSettings{} } func (*MachineControllerManagerSettings) ProtoMessage() {} func (*MachineControllerManagerSettings) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{94} + return fileDescriptor_ca37af0df9a5bbd2, []int{97} } func (m *MachineControllerManagerSettings) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2706,7 +2790,7 @@ var xxx_messageInfo_MachineControllerManagerSettings proto.InternalMessageInfo func (m *MachineImage) Reset() { *m = MachineImage{} } func (*MachineImage) ProtoMessage() {} func (*MachineImage) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{95} + return fileDescriptor_ca37af0df9a5bbd2, []int{98} } func (m *MachineImage) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2734,7 +2818,7 @@ var xxx_messageInfo_MachineImage proto.InternalMessageInfo func (m *MachineImageVersion) Reset() { *m = MachineImageVersion{} } func (*MachineImageVersion) ProtoMessage() {} func (*MachineImageVersion) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{96} + return fileDescriptor_ca37af0df9a5bbd2, []int{99} } func (m *MachineImageVersion) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2759,10 +2843,38 @@ func (m *MachineImageVersion) XXX_DiscardUnknown() { var xxx_messageInfo_MachineImageVersion proto.InternalMessageInfo +func (m *MachineImageVersionStatus) Reset() { *m = MachineImageVersionStatus{} } +func (*MachineImageVersionStatus) ProtoMessage() {} +func (*MachineImageVersionStatus) Descriptor() ([]byte, []int) { + return fileDescriptor_ca37af0df9a5bbd2, []int{100} +} +func (m *MachineImageVersionStatus) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MachineImageVersionStatus) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil +} +func (m *MachineImageVersionStatus) XXX_Merge(src proto.Message) { + xxx_messageInfo_MachineImageVersionStatus.Merge(m, src) +} +func (m *MachineImageVersionStatus) XXX_Size() int { + return m.Size() +} +func (m *MachineImageVersionStatus) XXX_DiscardUnknown() { + xxx_messageInfo_MachineImageVersionStatus.DiscardUnknown(m) +} + +var xxx_messageInfo_MachineImageVersionStatus proto.InternalMessageInfo + func (m *MachineType) Reset() { *m = MachineType{} } func (*MachineType) ProtoMessage() {} func (*MachineType) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{97} + return fileDescriptor_ca37af0df9a5bbd2, []int{101} } func (m *MachineType) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2790,7 +2902,7 @@ var xxx_messageInfo_MachineType proto.InternalMessageInfo func (m *MachineTypeStorage) Reset() { *m = MachineTypeStorage{} } func (*MachineTypeStorage) ProtoMessage() {} func (*MachineTypeStorage) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{98} + return fileDescriptor_ca37af0df9a5bbd2, []int{102} } func (m *MachineTypeStorage) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2818,7 +2930,7 @@ var xxx_messageInfo_MachineTypeStorage proto.InternalMessageInfo func (m *Maintenance) Reset() { *m = Maintenance{} } func (*Maintenance) ProtoMessage() {} func (*Maintenance) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{99} + return fileDescriptor_ca37af0df9a5bbd2, []int{103} } func (m *Maintenance) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2846,7 +2958,7 @@ var xxx_messageInfo_Maintenance proto.InternalMessageInfo func (m *MaintenanceAutoUpdate) Reset() { *m = MaintenanceAutoUpdate{} } func (*MaintenanceAutoUpdate) ProtoMessage() {} func (*MaintenanceAutoUpdate) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{100} + return fileDescriptor_ca37af0df9a5bbd2, []int{104} } func (m *MaintenanceAutoUpdate) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2874,7 +2986,7 @@ var xxx_messageInfo_MaintenanceAutoUpdate proto.InternalMessageInfo func (m *MaintenanceTimeWindow) Reset() { *m = MaintenanceTimeWindow{} } func (*MaintenanceTimeWindow) ProtoMessage() {} func (*MaintenanceTimeWindow) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{101} + return fileDescriptor_ca37af0df9a5bbd2, []int{105} } func (m *MaintenanceTimeWindow) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2902,7 +3014,7 @@ var xxx_messageInfo_MaintenanceTimeWindow proto.InternalMessageInfo func (m *MemorySwapConfiguration) Reset() { *m = MemorySwapConfiguration{} } func (*MemorySwapConfiguration) ProtoMessage() {} func (*MemorySwapConfiguration) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{102} + return fileDescriptor_ca37af0df9a5bbd2, []int{106} } func (m *MemorySwapConfiguration) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2930,7 +3042,7 @@ var xxx_messageInfo_MemorySwapConfiguration proto.InternalMessageInfo func (m *Monitoring) Reset() { *m = Monitoring{} } func (*Monitoring) ProtoMessage() {} func (*Monitoring) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{103} + return fileDescriptor_ca37af0df9a5bbd2, []int{107} } func (m *Monitoring) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2958,7 +3070,7 @@ var xxx_messageInfo_Monitoring proto.InternalMessageInfo func (m *NamedResourceReference) Reset() { *m = NamedResourceReference{} } func (*NamedResourceReference) ProtoMessage() {} func (*NamedResourceReference) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{104} + return fileDescriptor_ca37af0df9a5bbd2, []int{108} } func (m *NamedResourceReference) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2986,7 +3098,7 @@ var xxx_messageInfo_NamedResourceReference proto.InternalMessageInfo func (m *NamespacedCloudProfile) Reset() { *m = NamespacedCloudProfile{} } func (*NamespacedCloudProfile) ProtoMessage() {} func (*NamespacedCloudProfile) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{105} + return fileDescriptor_ca37af0df9a5bbd2, []int{109} } func (m *NamespacedCloudProfile) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3014,7 +3126,7 @@ var xxx_messageInfo_NamespacedCloudProfile proto.InternalMessageInfo func (m *NamespacedCloudProfileList) Reset() { *m = NamespacedCloudProfileList{} } func (*NamespacedCloudProfileList) ProtoMessage() {} func (*NamespacedCloudProfileList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{106} + return fileDescriptor_ca37af0df9a5bbd2, []int{110} } func (m *NamespacedCloudProfileList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3042,7 +3154,7 @@ var xxx_messageInfo_NamespacedCloudProfileList proto.InternalMessageInfo func (m *NamespacedCloudProfileSpec) Reset() { *m = NamespacedCloudProfileSpec{} } func (*NamespacedCloudProfileSpec) ProtoMessage() {} func (*NamespacedCloudProfileSpec) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{107} + return fileDescriptor_ca37af0df9a5bbd2, []int{111} } func (m *NamespacedCloudProfileSpec) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3070,7 +3182,7 @@ var xxx_messageInfo_NamespacedCloudProfileSpec proto.InternalMessageInfo func (m *NamespacedCloudProfileStatus) Reset() { *m = NamespacedCloudProfileStatus{} } func (*NamespacedCloudProfileStatus) ProtoMessage() {} func (*NamespacedCloudProfileStatus) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{108} + return fileDescriptor_ca37af0df9a5bbd2, []int{112} } func (m *NamespacedCloudProfileStatus) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3098,7 +3210,7 @@ var xxx_messageInfo_NamespacedCloudProfileStatus proto.InternalMessageInfo func (m *Networking) Reset() { *m = Networking{} } func (*Networking) ProtoMessage() {} func (*Networking) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{109} + return fileDescriptor_ca37af0df9a5bbd2, []int{113} } func (m *Networking) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3126,7 +3238,7 @@ var xxx_messageInfo_Networking proto.InternalMessageInfo func (m *NetworkingStatus) Reset() { *m = NetworkingStatus{} } func (*NetworkingStatus) ProtoMessage() {} func (*NetworkingStatus) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{110} + return fileDescriptor_ca37af0df9a5bbd2, []int{114} } func (m *NetworkingStatus) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3154,7 +3266,7 @@ var xxx_messageInfo_NetworkingStatus proto.InternalMessageInfo func (m *NginxIngress) Reset() { *m = NginxIngress{} } func (*NginxIngress) ProtoMessage() {} func (*NginxIngress) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{111} + return fileDescriptor_ca37af0df9a5bbd2, []int{115} } func (m *NginxIngress) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3182,7 +3294,7 @@ var xxx_messageInfo_NginxIngress proto.InternalMessageInfo func (m *NodeLocalDNS) Reset() { *m = NodeLocalDNS{} } func (*NodeLocalDNS) ProtoMessage() {} func (*NodeLocalDNS) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{112} + return fileDescriptor_ca37af0df9a5bbd2, []int{116} } func (m *NodeLocalDNS) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3210,7 +3322,7 @@ var xxx_messageInfo_NodeLocalDNS proto.InternalMessageInfo func (m *OCIRepository) Reset() { *m = OCIRepository{} } func (*OCIRepository) ProtoMessage() {} func (*OCIRepository) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{113} + return fileDescriptor_ca37af0df9a5bbd2, []int{117} } func (m *OCIRepository) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3238,7 +3350,7 @@ var xxx_messageInfo_OCIRepository proto.InternalMessageInfo func (m *OIDCConfig) Reset() { *m = OIDCConfig{} } func (*OIDCConfig) ProtoMessage() {} func (*OIDCConfig) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{114} + return fileDescriptor_ca37af0df9a5bbd2, []int{118} } func (m *OIDCConfig) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3266,7 +3378,7 @@ var xxx_messageInfo_OIDCConfig proto.InternalMessageInfo func (m *ObservabilityRotation) Reset() { *m = ObservabilityRotation{} } func (*ObservabilityRotation) ProtoMessage() {} func (*ObservabilityRotation) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{115} + return fileDescriptor_ca37af0df9a5bbd2, []int{119} } func (m *ObservabilityRotation) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3294,7 +3406,7 @@ var xxx_messageInfo_ObservabilityRotation proto.InternalMessageInfo func (m *OpenIDConnectClientAuthentication) Reset() { *m = OpenIDConnectClientAuthentication{} } func (*OpenIDConnectClientAuthentication) ProtoMessage() {} func (*OpenIDConnectClientAuthentication) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{116} + return fileDescriptor_ca37af0df9a5bbd2, []int{120} } func (m *OpenIDConnectClientAuthentication) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3322,7 +3434,7 @@ var xxx_messageInfo_OpenIDConnectClientAuthentication proto.InternalMessageInfo func (m *Project) Reset() { *m = Project{} } func (*Project) ProtoMessage() {} func (*Project) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{117} + return fileDescriptor_ca37af0df9a5bbd2, []int{121} } func (m *Project) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3350,7 +3462,7 @@ var xxx_messageInfo_Project proto.InternalMessageInfo func (m *ProjectList) Reset() { *m = ProjectList{} } func (*ProjectList) ProtoMessage() {} func (*ProjectList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{118} + return fileDescriptor_ca37af0df9a5bbd2, []int{122} } func (m *ProjectList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3378,7 +3490,7 @@ var xxx_messageInfo_ProjectList proto.InternalMessageInfo func (m *ProjectMember) Reset() { *m = ProjectMember{} } func (*ProjectMember) ProtoMessage() {} func (*ProjectMember) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{119} + return fileDescriptor_ca37af0df9a5bbd2, []int{123} } func (m *ProjectMember) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3406,7 +3518,7 @@ var xxx_messageInfo_ProjectMember proto.InternalMessageInfo func (m *ProjectSpec) Reset() { *m = ProjectSpec{} } func (*ProjectSpec) ProtoMessage() {} func (*ProjectSpec) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{120} + return fileDescriptor_ca37af0df9a5bbd2, []int{124} } func (m *ProjectSpec) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3434,7 +3546,7 @@ var xxx_messageInfo_ProjectSpec proto.InternalMessageInfo func (m *ProjectStatus) Reset() { *m = ProjectStatus{} } func (*ProjectStatus) ProtoMessage() {} func (*ProjectStatus) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{121} + return fileDescriptor_ca37af0df9a5bbd2, []int{125} } func (m *ProjectStatus) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3462,7 +3574,7 @@ var xxx_messageInfo_ProjectStatus proto.InternalMessageInfo func (m *ProjectTolerations) Reset() { *m = ProjectTolerations{} } func (*ProjectTolerations) ProtoMessage() {} func (*ProjectTolerations) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{122} + return fileDescriptor_ca37af0df9a5bbd2, []int{126} } func (m *ProjectTolerations) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3490,7 +3602,7 @@ var xxx_messageInfo_ProjectTolerations proto.InternalMessageInfo func (m *Provider) Reset() { *m = Provider{} } func (*Provider) ProtoMessage() {} func (*Provider) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{123} + return fileDescriptor_ca37af0df9a5bbd2, []int{127} } func (m *Provider) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3518,7 +3630,7 @@ var xxx_messageInfo_Provider proto.InternalMessageInfo func (m *Quota) Reset() { *m = Quota{} } func (*Quota) ProtoMessage() {} func (*Quota) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{124} + return fileDescriptor_ca37af0df9a5bbd2, []int{128} } func (m *Quota) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3546,7 +3658,7 @@ var xxx_messageInfo_Quota proto.InternalMessageInfo func (m *QuotaList) Reset() { *m = QuotaList{} } func (*QuotaList) ProtoMessage() {} func (*QuotaList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{125} + return fileDescriptor_ca37af0df9a5bbd2, []int{129} } func (m *QuotaList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3574,7 +3686,7 @@ var xxx_messageInfo_QuotaList proto.InternalMessageInfo func (m *QuotaSpec) Reset() { *m = QuotaSpec{} } func (*QuotaSpec) ProtoMessage() {} func (*QuotaSpec) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{126} + return fileDescriptor_ca37af0df9a5bbd2, []int{130} } func (m *QuotaSpec) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3602,7 +3714,7 @@ var xxx_messageInfo_QuotaSpec proto.InternalMessageInfo func (m *Region) Reset() { *m = Region{} } func (*Region) ProtoMessage() {} func (*Region) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{127} + return fileDescriptor_ca37af0df9a5bbd2, []int{131} } func (m *Region) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3630,7 +3742,7 @@ var xxx_messageInfo_Region proto.InternalMessageInfo func (m *ResourceData) Reset() { *m = ResourceData{} } func (*ResourceData) ProtoMessage() {} func (*ResourceData) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{128} + return fileDescriptor_ca37af0df9a5bbd2, []int{132} } func (m *ResourceData) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3658,7 +3770,7 @@ var xxx_messageInfo_ResourceData proto.InternalMessageInfo func (m *ResourceWatchCacheSize) Reset() { *m = ResourceWatchCacheSize{} } func (*ResourceWatchCacheSize) ProtoMessage() {} func (*ResourceWatchCacheSize) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{129} + return fileDescriptor_ca37af0df9a5bbd2, []int{133} } func (m *ResourceWatchCacheSize) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3686,7 +3798,7 @@ var xxx_messageInfo_ResourceWatchCacheSize proto.InternalMessageInfo func (m *SSHAccess) Reset() { *m = SSHAccess{} } func (*SSHAccess) ProtoMessage() {} func (*SSHAccess) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{130} + return fileDescriptor_ca37af0df9a5bbd2, []int{134} } func (m *SSHAccess) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3714,7 +3826,7 @@ var xxx_messageInfo_SSHAccess proto.InternalMessageInfo func (m *SecretBinding) Reset() { *m = SecretBinding{} } func (*SecretBinding) ProtoMessage() {} func (*SecretBinding) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{131} + return fileDescriptor_ca37af0df9a5bbd2, []int{135} } func (m *SecretBinding) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3742,7 +3854,7 @@ var xxx_messageInfo_SecretBinding proto.InternalMessageInfo func (m *SecretBindingList) Reset() { *m = SecretBindingList{} } func (*SecretBindingList) ProtoMessage() {} func (*SecretBindingList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{132} + return fileDescriptor_ca37af0df9a5bbd2, []int{136} } func (m *SecretBindingList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3770,7 +3882,7 @@ var xxx_messageInfo_SecretBindingList proto.InternalMessageInfo func (m *SecretBindingProvider) Reset() { *m = SecretBindingProvider{} } func (*SecretBindingProvider) ProtoMessage() {} func (*SecretBindingProvider) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{133} + return fileDescriptor_ca37af0df9a5bbd2, []int{137} } func (m *SecretBindingProvider) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3798,7 +3910,7 @@ var xxx_messageInfo_SecretBindingProvider proto.InternalMessageInfo func (m *Seed) Reset() { *m = Seed{} } func (*Seed) ProtoMessage() {} func (*Seed) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{134} + return fileDescriptor_ca37af0df9a5bbd2, []int{138} } func (m *Seed) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3826,7 +3938,7 @@ var xxx_messageInfo_Seed proto.InternalMessageInfo func (m *SeedBackup) Reset() { *m = SeedBackup{} } func (*SeedBackup) ProtoMessage() {} func (*SeedBackup) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{135} + return fileDescriptor_ca37af0df9a5bbd2, []int{139} } func (m *SeedBackup) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3854,7 +3966,7 @@ var xxx_messageInfo_SeedBackup proto.InternalMessageInfo func (m *SeedDNS) Reset() { *m = SeedDNS{} } func (*SeedDNS) ProtoMessage() {} func (*SeedDNS) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{136} + return fileDescriptor_ca37af0df9a5bbd2, []int{140} } func (m *SeedDNS) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3882,7 +3994,7 @@ var xxx_messageInfo_SeedDNS proto.InternalMessageInfo func (m *SeedDNSProvider) Reset() { *m = SeedDNSProvider{} } func (*SeedDNSProvider) ProtoMessage() {} func (*SeedDNSProvider) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{137} + return fileDescriptor_ca37af0df9a5bbd2, []int{141} } func (m *SeedDNSProvider) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3910,7 +4022,7 @@ var xxx_messageInfo_SeedDNSProvider proto.InternalMessageInfo func (m *SeedList) Reset() { *m = SeedList{} } func (*SeedList) ProtoMessage() {} func (*SeedList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{138} + return fileDescriptor_ca37af0df9a5bbd2, []int{142} } func (m *SeedList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3938,7 +4050,7 @@ var xxx_messageInfo_SeedList proto.InternalMessageInfo func (m *SeedNetworks) Reset() { *m = SeedNetworks{} } func (*SeedNetworks) ProtoMessage() {} func (*SeedNetworks) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{139} + return fileDescriptor_ca37af0df9a5bbd2, []int{143} } func (m *SeedNetworks) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3966,7 +4078,7 @@ var xxx_messageInfo_SeedNetworks proto.InternalMessageInfo func (m *SeedProvider) Reset() { *m = SeedProvider{} } func (*SeedProvider) ProtoMessage() {} func (*SeedProvider) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{140} + return fileDescriptor_ca37af0df9a5bbd2, []int{144} } func (m *SeedProvider) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -3994,7 +4106,7 @@ var xxx_messageInfo_SeedProvider proto.InternalMessageInfo func (m *SeedSelector) Reset() { *m = SeedSelector{} } func (*SeedSelector) ProtoMessage() {} func (*SeedSelector) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{141} + return fileDescriptor_ca37af0df9a5bbd2, []int{145} } func (m *SeedSelector) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4022,7 +4134,7 @@ var xxx_messageInfo_SeedSelector proto.InternalMessageInfo func (m *SeedSettingDependencyWatchdog) Reset() { *m = SeedSettingDependencyWatchdog{} } func (*SeedSettingDependencyWatchdog) ProtoMessage() {} func (*SeedSettingDependencyWatchdog) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{142} + return fileDescriptor_ca37af0df9a5bbd2, []int{146} } func (m *SeedSettingDependencyWatchdog) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4050,7 +4162,7 @@ var xxx_messageInfo_SeedSettingDependencyWatchdog proto.InternalMessageInfo func (m *SeedSettingDependencyWatchdogProber) Reset() { *m = SeedSettingDependencyWatchdogProber{} } func (*SeedSettingDependencyWatchdogProber) ProtoMessage() {} func (*SeedSettingDependencyWatchdogProber) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{143} + return fileDescriptor_ca37af0df9a5bbd2, []int{147} } func (m *SeedSettingDependencyWatchdogProber) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4078,7 +4190,7 @@ var xxx_messageInfo_SeedSettingDependencyWatchdogProber proto.InternalMessageInf func (m *SeedSettingDependencyWatchdogWeeder) Reset() { *m = SeedSettingDependencyWatchdogWeeder{} } func (*SeedSettingDependencyWatchdogWeeder) ProtoMessage() {} func (*SeedSettingDependencyWatchdogWeeder) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{144} + return fileDescriptor_ca37af0df9a5bbd2, []int{148} } func (m *SeedSettingDependencyWatchdogWeeder) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4106,7 +4218,7 @@ var xxx_messageInfo_SeedSettingDependencyWatchdogWeeder proto.InternalMessageInf func (m *SeedSettingExcessCapacityReservation) Reset() { *m = SeedSettingExcessCapacityReservation{} } func (*SeedSettingExcessCapacityReservation) ProtoMessage() {} func (*SeedSettingExcessCapacityReservation) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{145} + return fileDescriptor_ca37af0df9a5bbd2, []int{149} } func (m *SeedSettingExcessCapacityReservation) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4136,7 +4248,7 @@ func (m *SeedSettingExcessCapacityReservationConfig) Reset() { } func (*SeedSettingExcessCapacityReservationConfig) ProtoMessage() {} func (*SeedSettingExcessCapacityReservationConfig) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{146} + return fileDescriptor_ca37af0df9a5bbd2, []int{150} } func (m *SeedSettingExcessCapacityReservationConfig) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4164,7 +4276,7 @@ var xxx_messageInfo_SeedSettingExcessCapacityReservationConfig proto.InternalMes func (m *SeedSettingLoadBalancerServices) Reset() { *m = SeedSettingLoadBalancerServices{} } func (*SeedSettingLoadBalancerServices) ProtoMessage() {} func (*SeedSettingLoadBalancerServices) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{147} + return fileDescriptor_ca37af0df9a5bbd2, []int{151} } func (m *SeedSettingLoadBalancerServices) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4192,7 +4304,7 @@ var xxx_messageInfo_SeedSettingLoadBalancerServices proto.InternalMessageInfo func (m *SeedSettingLoadBalancerServicesZones) Reset() { *m = SeedSettingLoadBalancerServicesZones{} } func (*SeedSettingLoadBalancerServicesZones) ProtoMessage() {} func (*SeedSettingLoadBalancerServicesZones) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{148} + return fileDescriptor_ca37af0df9a5bbd2, []int{152} } func (m *SeedSettingLoadBalancerServicesZones) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4220,7 +4332,7 @@ var xxx_messageInfo_SeedSettingLoadBalancerServicesZones proto.InternalMessageIn func (m *SeedSettingScheduling) Reset() { *m = SeedSettingScheduling{} } func (*SeedSettingScheduling) ProtoMessage() {} func (*SeedSettingScheduling) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{149} + return fileDescriptor_ca37af0df9a5bbd2, []int{153} } func (m *SeedSettingScheduling) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4248,7 +4360,7 @@ var xxx_messageInfo_SeedSettingScheduling proto.InternalMessageInfo func (m *SeedSettingTopologyAwareRouting) Reset() { *m = SeedSettingTopologyAwareRouting{} } func (*SeedSettingTopologyAwareRouting) ProtoMessage() {} func (*SeedSettingTopologyAwareRouting) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{150} + return fileDescriptor_ca37af0df9a5bbd2, []int{154} } func (m *SeedSettingTopologyAwareRouting) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4276,7 +4388,7 @@ var xxx_messageInfo_SeedSettingTopologyAwareRouting proto.InternalMessageInfo func (m *SeedSettingVerticalPodAutoscaler) Reset() { *m = SeedSettingVerticalPodAutoscaler{} } func (*SeedSettingVerticalPodAutoscaler) ProtoMessage() {} func (*SeedSettingVerticalPodAutoscaler) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{151} + return fileDescriptor_ca37af0df9a5bbd2, []int{155} } func (m *SeedSettingVerticalPodAutoscaler) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4304,7 +4416,7 @@ var xxx_messageInfo_SeedSettingVerticalPodAutoscaler proto.InternalMessageInfo func (m *SeedSettings) Reset() { *m = SeedSettings{} } func (*SeedSettings) ProtoMessage() {} func (*SeedSettings) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{152} + return fileDescriptor_ca37af0df9a5bbd2, []int{156} } func (m *SeedSettings) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4332,7 +4444,7 @@ var xxx_messageInfo_SeedSettings proto.InternalMessageInfo func (m *SeedSpec) Reset() { *m = SeedSpec{} } func (*SeedSpec) ProtoMessage() {} func (*SeedSpec) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{153} + return fileDescriptor_ca37af0df9a5bbd2, []int{157} } func (m *SeedSpec) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4360,7 +4472,7 @@ var xxx_messageInfo_SeedSpec proto.InternalMessageInfo func (m *SeedStatus) Reset() { *m = SeedStatus{} } func (*SeedStatus) ProtoMessage() {} func (*SeedStatus) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{154} + return fileDescriptor_ca37af0df9a5bbd2, []int{158} } func (m *SeedStatus) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4388,7 +4500,7 @@ var xxx_messageInfo_SeedStatus proto.InternalMessageInfo func (m *SeedTaint) Reset() { *m = SeedTaint{} } func (*SeedTaint) ProtoMessage() {} func (*SeedTaint) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{155} + return fileDescriptor_ca37af0df9a5bbd2, []int{159} } func (m *SeedTaint) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4416,7 +4528,7 @@ var xxx_messageInfo_SeedTaint proto.InternalMessageInfo func (m *SeedTemplate) Reset() { *m = SeedTemplate{} } func (*SeedTemplate) ProtoMessage() {} func (*SeedTemplate) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{156} + return fileDescriptor_ca37af0df9a5bbd2, []int{160} } func (m *SeedTemplate) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4444,7 +4556,7 @@ var xxx_messageInfo_SeedTemplate proto.InternalMessageInfo func (m *SeedVolume) Reset() { *m = SeedVolume{} } func (*SeedVolume) ProtoMessage() {} func (*SeedVolume) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{157} + return fileDescriptor_ca37af0df9a5bbd2, []int{161} } func (m *SeedVolume) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4472,7 +4584,7 @@ var xxx_messageInfo_SeedVolume proto.InternalMessageInfo func (m *SeedVolumeProvider) Reset() { *m = SeedVolumeProvider{} } func (*SeedVolumeProvider) ProtoMessage() {} func (*SeedVolumeProvider) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{158} + return fileDescriptor_ca37af0df9a5bbd2, []int{162} } func (m *SeedVolumeProvider) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4500,7 +4612,7 @@ var xxx_messageInfo_SeedVolumeProvider proto.InternalMessageInfo func (m *ServiceAccountConfig) Reset() { *m = ServiceAccountConfig{} } func (*ServiceAccountConfig) ProtoMessage() {} func (*ServiceAccountConfig) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{159} + return fileDescriptor_ca37af0df9a5bbd2, []int{163} } func (m *ServiceAccountConfig) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4528,7 +4640,7 @@ var xxx_messageInfo_ServiceAccountConfig proto.InternalMessageInfo func (m *ServiceAccountKeyRotation) Reset() { *m = ServiceAccountKeyRotation{} } func (*ServiceAccountKeyRotation) ProtoMessage() {} func (*ServiceAccountKeyRotation) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{160} + return fileDescriptor_ca37af0df9a5bbd2, []int{164} } func (m *ServiceAccountKeyRotation) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4556,7 +4668,7 @@ var xxx_messageInfo_ServiceAccountKeyRotation proto.InternalMessageInfo func (m *Shoot) Reset() { *m = Shoot{} } func (*Shoot) ProtoMessage() {} func (*Shoot) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{161} + return fileDescriptor_ca37af0df9a5bbd2, []int{165} } func (m *Shoot) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4584,7 +4696,7 @@ var xxx_messageInfo_Shoot proto.InternalMessageInfo func (m *ShootAdvertisedAddress) Reset() { *m = ShootAdvertisedAddress{} } func (*ShootAdvertisedAddress) ProtoMessage() {} func (*ShootAdvertisedAddress) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{162} + return fileDescriptor_ca37af0df9a5bbd2, []int{166} } func (m *ShootAdvertisedAddress) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4612,7 +4724,7 @@ var xxx_messageInfo_ShootAdvertisedAddress proto.InternalMessageInfo func (m *ShootCredentials) Reset() { *m = ShootCredentials{} } func (*ShootCredentials) ProtoMessage() {} func (*ShootCredentials) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{163} + return fileDescriptor_ca37af0df9a5bbd2, []int{167} } func (m *ShootCredentials) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4640,7 +4752,7 @@ var xxx_messageInfo_ShootCredentials proto.InternalMessageInfo func (m *ShootCredentialsRotation) Reset() { *m = ShootCredentialsRotation{} } func (*ShootCredentialsRotation) ProtoMessage() {} func (*ShootCredentialsRotation) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{164} + return fileDescriptor_ca37af0df9a5bbd2, []int{168} } func (m *ShootCredentialsRotation) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4668,7 +4780,7 @@ var xxx_messageInfo_ShootCredentialsRotation proto.InternalMessageInfo func (m *ShootKubeconfigRotation) Reset() { *m = ShootKubeconfigRotation{} } func (*ShootKubeconfigRotation) ProtoMessage() {} func (*ShootKubeconfigRotation) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{165} + return fileDescriptor_ca37af0df9a5bbd2, []int{169} } func (m *ShootKubeconfigRotation) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4696,7 +4808,7 @@ var xxx_messageInfo_ShootKubeconfigRotation proto.InternalMessageInfo func (m *ShootList) Reset() { *m = ShootList{} } func (*ShootList) ProtoMessage() {} func (*ShootList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{166} + return fileDescriptor_ca37af0df9a5bbd2, []int{170} } func (m *ShootList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4724,7 +4836,7 @@ var xxx_messageInfo_ShootList proto.InternalMessageInfo func (m *ShootMachineImage) Reset() { *m = ShootMachineImage{} } func (*ShootMachineImage) ProtoMessage() {} func (*ShootMachineImage) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{167} + return fileDescriptor_ca37af0df9a5bbd2, []int{171} } func (m *ShootMachineImage) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4752,7 +4864,7 @@ var xxx_messageInfo_ShootMachineImage proto.InternalMessageInfo func (m *ShootNetworks) Reset() { *m = ShootNetworks{} } func (*ShootNetworks) ProtoMessage() {} func (*ShootNetworks) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{168} + return fileDescriptor_ca37af0df9a5bbd2, []int{172} } func (m *ShootNetworks) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4780,7 +4892,7 @@ var xxx_messageInfo_ShootNetworks proto.InternalMessageInfo func (m *ShootSSHKeypairRotation) Reset() { *m = ShootSSHKeypairRotation{} } func (*ShootSSHKeypairRotation) ProtoMessage() {} func (*ShootSSHKeypairRotation) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{169} + return fileDescriptor_ca37af0df9a5bbd2, []int{173} } func (m *ShootSSHKeypairRotation) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4808,7 +4920,7 @@ var xxx_messageInfo_ShootSSHKeypairRotation proto.InternalMessageInfo func (m *ShootSpec) Reset() { *m = ShootSpec{} } func (*ShootSpec) ProtoMessage() {} func (*ShootSpec) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{170} + return fileDescriptor_ca37af0df9a5bbd2, []int{174} } func (m *ShootSpec) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4836,7 +4948,7 @@ var xxx_messageInfo_ShootSpec proto.InternalMessageInfo func (m *ShootState) Reset() { *m = ShootState{} } func (*ShootState) ProtoMessage() {} func (*ShootState) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{171} + return fileDescriptor_ca37af0df9a5bbd2, []int{175} } func (m *ShootState) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4864,7 +4976,7 @@ var xxx_messageInfo_ShootState proto.InternalMessageInfo func (m *ShootStateList) Reset() { *m = ShootStateList{} } func (*ShootStateList) ProtoMessage() {} func (*ShootStateList) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{172} + return fileDescriptor_ca37af0df9a5bbd2, []int{176} } func (m *ShootStateList) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4892,7 +5004,7 @@ var xxx_messageInfo_ShootStateList proto.InternalMessageInfo func (m *ShootStateSpec) Reset() { *m = ShootStateSpec{} } func (*ShootStateSpec) ProtoMessage() {} func (*ShootStateSpec) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{173} + return fileDescriptor_ca37af0df9a5bbd2, []int{177} } func (m *ShootStateSpec) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4920,7 +5032,7 @@ var xxx_messageInfo_ShootStateSpec proto.InternalMessageInfo func (m *ShootStatus) Reset() { *m = ShootStatus{} } func (*ShootStatus) ProtoMessage() {} func (*ShootStatus) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{174} + return fileDescriptor_ca37af0df9a5bbd2, []int{178} } func (m *ShootStatus) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4948,7 +5060,7 @@ var xxx_messageInfo_ShootStatus proto.InternalMessageInfo func (m *ShootTemplate) Reset() { *m = ShootTemplate{} } func (*ShootTemplate) ProtoMessage() {} func (*ShootTemplate) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{175} + return fileDescriptor_ca37af0df9a5bbd2, []int{179} } func (m *ShootTemplate) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -4976,7 +5088,7 @@ var xxx_messageInfo_ShootTemplate proto.InternalMessageInfo func (m *StructuredAuthentication) Reset() { *m = StructuredAuthentication{} } func (*StructuredAuthentication) ProtoMessage() {} func (*StructuredAuthentication) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{176} + return fileDescriptor_ca37af0df9a5bbd2, []int{180} } func (m *StructuredAuthentication) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5004,7 +5116,7 @@ var xxx_messageInfo_StructuredAuthentication proto.InternalMessageInfo func (m *StructuredAuthorization) Reset() { *m = StructuredAuthorization{} } func (*StructuredAuthorization) ProtoMessage() {} func (*StructuredAuthorization) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{177} + return fileDescriptor_ca37af0df9a5bbd2, []int{181} } func (m *StructuredAuthorization) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5032,7 +5144,7 @@ var xxx_messageInfo_StructuredAuthorization proto.InternalMessageInfo func (m *SystemComponents) Reset() { *m = SystemComponents{} } func (*SystemComponents) ProtoMessage() {} func (*SystemComponents) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{178} + return fileDescriptor_ca37af0df9a5bbd2, []int{182} } func (m *SystemComponents) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5060,7 +5172,7 @@ var xxx_messageInfo_SystemComponents proto.InternalMessageInfo func (m *Toleration) Reset() { *m = Toleration{} } func (*Toleration) ProtoMessage() {} func (*Toleration) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{179} + return fileDescriptor_ca37af0df9a5bbd2, []int{183} } func (m *Toleration) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5088,7 +5200,7 @@ var xxx_messageInfo_Toleration proto.InternalMessageInfo func (m *VerticalPodAutoscaler) Reset() { *m = VerticalPodAutoscaler{} } func (*VerticalPodAutoscaler) ProtoMessage() {} func (*VerticalPodAutoscaler) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{180} + return fileDescriptor_ca37af0df9a5bbd2, []int{184} } func (m *VerticalPodAutoscaler) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5116,7 +5228,7 @@ var xxx_messageInfo_VerticalPodAutoscaler proto.InternalMessageInfo func (m *Volume) Reset() { *m = Volume{} } func (*Volume) ProtoMessage() {} func (*Volume) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{181} + return fileDescriptor_ca37af0df9a5bbd2, []int{185} } func (m *Volume) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5144,7 +5256,7 @@ var xxx_messageInfo_Volume proto.InternalMessageInfo func (m *VolumeType) Reset() { *m = VolumeType{} } func (*VolumeType) ProtoMessage() {} func (*VolumeType) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{182} + return fileDescriptor_ca37af0df9a5bbd2, []int{186} } func (m *VolumeType) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5172,7 +5284,7 @@ var xxx_messageInfo_VolumeType proto.InternalMessageInfo func (m *WatchCacheSizes) Reset() { *m = WatchCacheSizes{} } func (*WatchCacheSizes) ProtoMessage() {} func (*WatchCacheSizes) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{183} + return fileDescriptor_ca37af0df9a5bbd2, []int{187} } func (m *WatchCacheSizes) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5200,7 +5312,7 @@ var xxx_messageInfo_WatchCacheSizes proto.InternalMessageInfo func (m *Worker) Reset() { *m = Worker{} } func (*Worker) ProtoMessage() {} func (*Worker) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{184} + return fileDescriptor_ca37af0df9a5bbd2, []int{188} } func (m *Worker) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5228,7 +5340,7 @@ var xxx_messageInfo_Worker proto.InternalMessageInfo func (m *WorkerKubernetes) Reset() { *m = WorkerKubernetes{} } func (*WorkerKubernetes) ProtoMessage() {} func (*WorkerKubernetes) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{185} + return fileDescriptor_ca37af0df9a5bbd2, []int{189} } func (m *WorkerKubernetes) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5256,7 +5368,7 @@ var xxx_messageInfo_WorkerKubernetes proto.InternalMessageInfo func (m *WorkerSystemComponents) Reset() { *m = WorkerSystemComponents{} } func (*WorkerSystemComponents) ProtoMessage() {} func (*WorkerSystemComponents) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{186} + return fileDescriptor_ca37af0df9a5bbd2, []int{190} } func (m *WorkerSystemComponents) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5284,7 +5396,7 @@ var xxx_messageInfo_WorkerSystemComponents proto.InternalMessageInfo func (m *WorkersSettings) Reset() { *m = WorkersSettings{} } func (*WorkersSettings) ProtoMessage() {} func (*WorkersSettings) Descriptor() ([]byte, []int) { - return fileDescriptor_ca37af0df9a5bbd2, []int{187} + return fileDescriptor_ca37af0df9a5bbd2, []int{191} } func (m *WorkersSettings) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -5341,6 +5453,7 @@ func init() { proto.RegisterType((*CloudProfileList)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.CloudProfileList") proto.RegisterType((*CloudProfileReference)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.CloudProfileReference") proto.RegisterType((*CloudProfileSpec)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.CloudProfileSpec") + proto.RegisterType((*CloudProfileStatus)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.CloudProfileStatus") proto.RegisterType((*ClusterAutoscaler)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.ClusterAutoscaler") proto.RegisterType((*ClusterAutoscalerOptions)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.ClusterAutoscalerOptions") proto.RegisterType((*Condition)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.Condition") @@ -5370,6 +5483,7 @@ func init() { proto.RegisterType((*ETCDEncryptionKeyRotation)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.ETCDEncryptionKeyRotation") proto.RegisterType((*EncryptionConfig)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.EncryptionConfig") proto.RegisterType((*ExpirableVersion)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.ExpirableVersion") + proto.RegisterType((*ExpirableVersionStatus)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.ExpirableVersionStatus") proto.RegisterType((*ExposureClass)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.ExposureClass") proto.RegisterType((*ExposureClassList)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.ExposureClassList") proto.RegisterType((*ExposureClassScheduling)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.ExposureClassScheduling") @@ -5408,11 +5522,13 @@ func init() { proto.RegisterType((*LastError)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.LastError") proto.RegisterType((*LastMaintenance)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.LastMaintenance") proto.RegisterType((*LastOperation)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.LastOperation") + proto.RegisterType((*LifecycleStage)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.LifecycleStage") proto.RegisterType((*LoadBalancerServicesProxyProtocol)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.LoadBalancerServicesProxyProtocol") proto.RegisterType((*Machine)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.Machine") proto.RegisterType((*MachineControllerManagerSettings)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.MachineControllerManagerSettings") proto.RegisterType((*MachineImage)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.MachineImage") proto.RegisterType((*MachineImageVersion)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.MachineImageVersion") + proto.RegisterType((*MachineImageVersionStatus)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.MachineImageVersionStatus") proto.RegisterType((*MachineType)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.MachineType") proto.RegisterType((*MachineTypeStorage)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.MachineTypeStorage") proto.RegisterType((*Maintenance)(nil), "github.com.gardener.gardener.pkg.apis.core.v1beta1.Maintenance") @@ -5525,836 +5641,846 @@ func init() { } var fileDescriptor_ca37af0df9a5bbd2 = []byte{ - // 13262 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xec, 0xbd, 0x7d, 0x70, 0x25, 0xd9, - 0x55, 0x18, 0xee, 0x7e, 0xfa, 0x3e, 0xfa, 0x18, 0xe9, 0xce, 0x97, 0x56, 0xbb, 0x3b, 0x6f, 0xdc, - 0xbb, 0xeb, 0xdf, 0x2e, 0x6b, 0x6b, 0xd8, 0x65, 0xed, 0xf5, 0xce, 0xb2, 0xbb, 0x96, 0x9e, 0x34, - 0x33, 0xcf, 0x23, 0x69, 0xe4, 0xf3, 0x34, 0xbb, 0xcb, 0x02, 0x0b, 0xad, 0xf7, 0xae, 0x9e, 0x7a, - 0xa7, 0x5f, 0xf7, 0xdb, 0xee, 0x7e, 0x1a, 0x69, 0xd6, 0xfe, 0x19, 0xfb, 0xc7, 0x87, 0x6d, 0x30, - 0x05, 0xfc, 0x92, 0xb8, 0xd6, 0x86, 0xc2, 0x84, 0x02, 0x92, 0x90, 0x72, 0x52, 0xa4, 0x48, 0x15, - 0x50, 0xa9, 0x4a, 0xa8, 0x4a, 0xb0, 0x29, 0xa0, 0x28, 0x20, 0x15, 0x53, 0x09, 0x22, 0x56, 0x08, - 0xa4, 0x2a, 0x29, 0x2a, 0x15, 0x2a, 0xa1, 0x98, 0x50, 0x90, 0xba, 0x1f, 0xdd, 0x7d, 0xfb, 0xeb, - 0xe9, 0xa9, 0x9f, 0x24, 0x7b, 0x03, 0x7f, 0x49, 0xef, 0x9e, 0x7b, 0xcf, 0xb9, 0x5f, 0x7d, 0xee, - 0x39, 0xe7, 0x9e, 0x7b, 0x0e, 0x2c, 0x36, 0x4d, 0x7f, 0xbb, 0xb3, 0x39, 0x5f, 0x77, 0x5a, 0x57, - 0x9a, 0x86, 0xdb, 0xa0, 0x36, 0x75, 0xa3, 0x7f, 0xda, 0x77, 0x9a, 0x57, 0x8c, 0xb6, 0xe9, 0x5d, - 0xa9, 0x3b, 0x2e, 0xbd, 0xb2, 0xf3, 0xd4, 0x26, 0xf5, 0x8d, 0xa7, 0xae, 0x34, 0x19, 0xcc, 0xf0, - 0x69, 0x63, 0xbe, 0xed, 0x3a, 0xbe, 0x43, 0x9e, 0x8e, 0x70, 0xcc, 0x07, 0x4d, 0xa3, 0x7f, 0xda, - 0x77, 0x9a, 0xf3, 0x0c, 0xc7, 0x3c, 0xc3, 0x31, 0x2f, 0x71, 0xcc, 0xbd, 0x4f, 0xa5, 0xeb, 0x34, - 0x9d, 0x2b, 0x1c, 0xd5, 0x66, 0x67, 0x8b, 0xff, 0xe2, 0x3f, 0xf8, 0x7f, 0x82, 0xc4, 0xdc, 0x13, - 0x77, 0x3e, 0xe8, 0xcd, 0x9b, 0x0e, 0xeb, 0xcc, 0x15, 0xa3, 0xe3, 0x3b, 0x5e, 0xdd, 0xb0, 0x4c, - 0xbb, 0x79, 0x65, 0x27, 0xd5, 0x9b, 0x39, 0x5d, 0xa9, 0x2a, 0xbb, 0xdd, 0xb5, 0x8e, 0xbb, 0x69, - 0xd4, 0xb3, 0xea, 0xdc, 0x88, 0xea, 0xd0, 0x5d, 0x9f, 0xda, 0x9e, 0xe9, 0xd8, 0xde, 0xfb, 0xd8, - 0x48, 0xa8, 0xbb, 0xa3, 0xce, 0x4d, 0xac, 0x42, 0x16, 0xa6, 0x67, 0x22, 0x4c, 0x2d, 0xa3, 0xbe, - 0x6d, 0xda, 0xd4, 0xdd, 0x0b, 0x9a, 0x5f, 0x71, 0xa9, 0xe7, 0x74, 0xdc, 0x3a, 0x3d, 0x52, 0x2b, - 0xef, 0x4a, 0x8b, 0xfa, 0x46, 0x16, 0xad, 0x2b, 0x79, 0xad, 0xdc, 0x8e, 0xed, 0x9b, 0xad, 0x34, - 0x99, 0x0f, 0x1c, 0xd6, 0xc0, 0xab, 0x6f, 0xd3, 0x96, 0x91, 0x6a, 0xf7, 0x2d, 0x79, 0xed, 0x3a, - 0xbe, 0x69, 0x5d, 0x31, 0x6d, 0xdf, 0xf3, 0xdd, 0x64, 0x23, 0xfd, 0x33, 0x1a, 0x4c, 0x2f, 0xac, - 0x57, 0x6b, 0x7c, 0x06, 0x57, 0x9c, 0x66, 0xd3, 0xb4, 0x9b, 0xe4, 0x49, 0x18, 0xdb, 0xa1, 0xee, - 0xa6, 0xe3, 0x99, 0xfe, 0xde, 0xac, 0x76, 0x59, 0x7b, 0x7c, 0x68, 0x71, 0xf2, 0x60, 0xbf, 0x3c, - 0xf6, 0x72, 0x50, 0x88, 0x11, 0x9c, 0x54, 0xe1, 0xec, 0xb6, 0xef, 0xb7, 0x17, 0xea, 0x75, 0xea, - 0x79, 0x61, 0x8d, 0xd9, 0x12, 0x6f, 0x76, 0xf1, 0x60, 0xbf, 0x7c, 0xf6, 0xc6, 0xc6, 0xc6, 0x7a, - 0x02, 0x8c, 0x59, 0x6d, 0xf4, 0x5f, 0xd0, 0x60, 0x26, 0xec, 0x0c, 0xd2, 0x37, 0x3b, 0xd4, 0xf3, - 0x3d, 0x82, 0x70, 0xa1, 0x65, 0xec, 0xae, 0x39, 0xf6, 0x6a, 0xc7, 0x37, 0x7c, 0xd3, 0x6e, 0x56, - 0xed, 0x2d, 0xcb, 0x6c, 0x6e, 0xfb, 0xb2, 0x6b, 0x73, 0x07, 0xfb, 0xe5, 0x0b, 0xab, 0x99, 0x35, - 0x30, 0xa7, 0x25, 0xeb, 0x74, 0xcb, 0xd8, 0x4d, 0x21, 0x54, 0x3a, 0xbd, 0x9a, 0x06, 0x63, 0x56, - 0x1b, 0xfd, 0xfd, 0x30, 0x23, 0xc6, 0x81, 0xd4, 0xf3, 0x5d, 0xb3, 0xee, 0x9b, 0x8e, 0x4d, 0x2e, - 0xc3, 0xa0, 0x6d, 0xb4, 0x28, 0xef, 0xe1, 0xd8, 0xe2, 0xc4, 0x97, 0xf7, 0xcb, 0xef, 0x3a, 0xd8, - 0x2f, 0x0f, 0xae, 0x19, 0x2d, 0x8a, 0x1c, 0xa2, 0xff, 0xaf, 0x12, 0x3c, 0x94, 0x6a, 0xf7, 0x8a, - 0xe9, 0x6f, 0xdf, 0x6a, 0xb3, 0xff, 0x3c, 0xf2, 0xc3, 0x1a, 0xcc, 0x18, 0xc9, 0x0a, 0x1c, 0xe1, - 0xf8, 0xd3, 0xcb, 0xf3, 0x47, 0xff, 0xc0, 0xe7, 0x53, 0xd4, 0x16, 0x1f, 0x90, 0xfd, 0x4a, 0x0f, - 0x00, 0xd3, 0xa4, 0xc9, 0xa7, 0x34, 0x18, 0x71, 0x44, 0xe7, 0x66, 0x4b, 0x97, 0x07, 0x1e, 0x1f, - 0x7f, 0xfa, 0x3b, 0x8f, 0xa5, 0x1b, 0xca, 0xa0, 0xe7, 0xe5, 0xdf, 0x65, 0xdb, 0x77, 0xf7, 0x16, - 0xcf, 0xc8, 0xee, 0x8d, 0xc8, 0x52, 0x0c, 0xc8, 0xcf, 0x5d, 0x85, 0x09, 0xb5, 0x26, 0x99, 0x86, - 0x81, 0x3b, 0x54, 0x6c, 0xd5, 0x31, 0x64, 0xff, 0x92, 0x73, 0x30, 0xb4, 0x63, 0x58, 0x1d, 0xca, - 0x97, 0x74, 0x0c, 0xc5, 0x8f, 0xab, 0xa5, 0x0f, 0x6a, 0xfa, 0xd3, 0x30, 0xb4, 0xd0, 0x68, 0x38, - 0x36, 0x79, 0x02, 0x46, 0xa8, 0x6d, 0x6c, 0x5a, 0xb4, 0xc1, 0x1b, 0x8e, 0x46, 0xf4, 0x96, 0x45, - 0x31, 0x06, 0x70, 0xfd, 0xef, 0x96, 0x60, 0x98, 0x37, 0xf2, 0xc8, 0x8f, 0x69, 0x70, 0xf6, 0x4e, - 0x67, 0x93, 0xba, 0x36, 0xf5, 0xa9, 0xb7, 0x64, 0x78, 0xdb, 0x9b, 0x8e, 0xe1, 0x36, 0xe4, 0xc2, - 0x5c, 0x2f, 0x32, 0x23, 0x37, 0xd3, 0xe8, 0xc4, 0x1e, 0xcc, 0x00, 0x60, 0x16, 0x71, 0xb2, 0x03, - 0x13, 0x76, 0xd3, 0xb4, 0x77, 0xab, 0x76, 0xd3, 0xa5, 0x9e, 0xc7, 0x07, 0x3d, 0xfe, 0xf4, 0x87, - 0x8a, 0x74, 0x66, 0x4d, 0xc1, 0xb3, 0x38, 0x7d, 0xb0, 0x5f, 0x9e, 0x50, 0x4b, 0x30, 0x46, 0x47, - 0xff, 0x2b, 0x0d, 0xce, 0x2c, 0x34, 0x5a, 0xa6, 0xc7, 0x38, 0xed, 0xba, 0xd5, 0x69, 0x9a, 0x3d, - 0x6c, 0x7d, 0xf2, 0x11, 0x18, 0xae, 0x3b, 0xf6, 0x96, 0xd9, 0x94, 0xfd, 0x7c, 0xdf, 0xbc, 0xe0, - 0x5c, 0xf3, 0x2a, 0xe7, 0xe2, 0xdd, 0x93, 0x1c, 0x6f, 0x1e, 0x8d, 0xbb, 0xcb, 0x01, 0x43, 0x5f, - 0x84, 0x83, 0xfd, 0xf2, 0x70, 0x85, 0x23, 0x40, 0x89, 0x88, 0x3c, 0x0e, 0xa3, 0x0d, 0xd3, 0x13, - 0x8b, 0x39, 0xc0, 0x17, 0x73, 0xe2, 0x60, 0xbf, 0x3c, 0xba, 0x24, 0xcb, 0x30, 0x84, 0x92, 0x15, - 0x38, 0xc7, 0x66, 0x50, 0xb4, 0xab, 0xd1, 0xba, 0x4b, 0x7d, 0xd6, 0xb5, 0xd9, 0x41, 0xde, 0xdd, - 0xd9, 0x83, 0xfd, 0xf2, 0xb9, 0x9b, 0x19, 0x70, 0xcc, 0x6c, 0xa5, 0x5f, 0x83, 0xd1, 0x05, 0x8b, - 0xba, 0x8c, 0x21, 0x90, 0xab, 0x30, 0x45, 0x5b, 0x86, 0x69, 0x21, 0xad, 0x53, 0x73, 0x87, 0xba, - 0xde, 0xac, 0x76, 0x79, 0xe0, 0xf1, 0xb1, 0x45, 0x72, 0xb0, 0x5f, 0x9e, 0x5a, 0x8e, 0x41, 0x30, - 0x51, 0x53, 0xff, 0x84, 0x06, 0xe3, 0x0b, 0x9d, 0x86, 0xe9, 0x8b, 0x71, 0x11, 0x17, 0xc6, 0x0d, - 0xf6, 0x73, 0xdd, 0xb1, 0xcc, 0xfa, 0x9e, 0xdc, 0x5c, 0x2f, 0x15, 0xfa, 0xdc, 0x22, 0x34, 0x8b, - 0x67, 0x0e, 0xf6, 0xcb, 0xe3, 0x4a, 0x01, 0xaa, 0x44, 0xf4, 0x6d, 0x50, 0x61, 0xe4, 0xdb, 0x60, - 0x42, 0x0c, 0x77, 0xd5, 0x68, 0x23, 0xdd, 0x92, 0x7d, 0x78, 0x44, 0x59, 0xab, 0x80, 0xd0, 0xfc, - 0xad, 0xcd, 0x37, 0x68, 0xdd, 0x47, 0xba, 0x45, 0x5d, 0x6a, 0xd7, 0xa9, 0xd8, 0x36, 0x15, 0xa5, - 0x31, 0xc6, 0x50, 0xe9, 0xff, 0xbf, 0x06, 0x0f, 0x2f, 0x74, 0xfc, 0x6d, 0xc7, 0x35, 0xef, 0x51, - 0x37, 0x9a, 0xee, 0x10, 0x03, 0x79, 0x11, 0xa6, 0x8c, 0xb0, 0xc2, 0x5a, 0xb4, 0x9d, 0x2e, 0xc8, - 0xed, 0x34, 0xb5, 0x10, 0x83, 0x62, 0xa2, 0x36, 0x79, 0x1a, 0xc0, 0x8b, 0xd6, 0x96, 0xf3, 0x80, - 0x45, 0x22, 0xdb, 0x82, 0xb2, 0xaa, 0x4a, 0x2d, 0xfd, 0x0f, 0xd9, 0x51, 0xb8, 0x63, 0x98, 0x96, - 0xb1, 0x69, 0x5a, 0xa6, 0xbf, 0xf7, 0x9a, 0x63, 0xd3, 0x1e, 0x76, 0xf3, 0x6d, 0xb8, 0xd8, 0xb1, - 0x0d, 0xd1, 0xce, 0xa2, 0xab, 0x62, 0xff, 0x6e, 0xec, 0xb5, 0xa9, 0xe0, 0x92, 0x63, 0x8b, 0x0f, - 0x1e, 0xec, 0x97, 0x2f, 0xde, 0xce, 0xae, 0x82, 0x79, 0x6d, 0xd9, 0xa9, 0xa7, 0x80, 0x5e, 0x76, - 0xac, 0x4e, 0x4b, 0x62, 0x1d, 0xe0, 0x58, 0xf9, 0xa9, 0x77, 0x3b, 0xb3, 0x06, 0xe6, 0xb4, 0xd4, - 0xbf, 0x5c, 0x82, 0x89, 0x45, 0xa3, 0x7e, 0xa7, 0xd3, 0x5e, 0xec, 0xd4, 0xef, 0x50, 0x9f, 0x7c, - 0x37, 0x8c, 0x32, 0xb1, 0xa5, 0x61, 0xf8, 0x86, 0x5c, 0xdf, 0x6f, 0xce, 0xfd, 0x16, 0xf9, 0xd6, - 0x62, 0xb5, 0xa3, 0x15, 0x5f, 0xa5, 0xbe, 0x11, 0x4d, 0x6b, 0x54, 0x86, 0x21, 0x56, 0xb2, 0x05, - 0x83, 0x5e, 0x9b, 0xd6, 0xe5, 0x97, 0xbe, 0x54, 0x64, 0x07, 0xab, 0x3d, 0xae, 0xb5, 0x69, 0x3d, - 0x5a, 0x05, 0xf6, 0x0b, 0x39, 0x7e, 0x62, 0xc3, 0xb0, 0xe7, 0x1b, 0x7e, 0xc7, 0xe3, 0x9f, 0xff, - 0xf8, 0xd3, 0xd7, 0xfa, 0xa6, 0xc4, 0xb1, 0x2d, 0x4e, 0x49, 0x5a, 0xc3, 0xe2, 0x37, 0x4a, 0x2a, - 0xfa, 0xbf, 0xd3, 0x60, 0x5a, 0xad, 0xbe, 0x62, 0x7a, 0x3e, 0xf9, 0x8e, 0xd4, 0x74, 0xce, 0xf7, - 0x36, 0x9d, 0xac, 0x35, 0x9f, 0xcc, 0x69, 0x49, 0x6e, 0x34, 0x28, 0x51, 0xa6, 0x92, 0xc2, 0x90, - 0xe9, 0xd3, 0x56, 0x70, 0xf8, 0x7e, 0xa8, 0xdf, 0x11, 0x2e, 0x4e, 0x4a, 0x62, 0x43, 0x55, 0x86, - 0x16, 0x05, 0x76, 0xfd, 0xbb, 0xe1, 0x9c, 0x5a, 0x6b, 0xdd, 0x75, 0x76, 0xcc, 0x06, 0x75, 0xd9, - 0x97, 0xe0, 0xef, 0xb5, 0x53, 0x5f, 0x02, 0xdb, 0x59, 0xc8, 0x21, 0xe4, 0x3d, 0x30, 0xec, 0xd2, - 0x26, 0x93, 0x52, 0xc4, 0x07, 0x17, 0xce, 0x1d, 0xf2, 0x52, 0x94, 0x50, 0xfd, 0x7f, 0x96, 0xe2, - 0x73, 0xc7, 0x96, 0x91, 0xec, 0xc0, 0x68, 0x5b, 0x92, 0x92, 0x73, 0x77, 0xa3, 0xdf, 0x01, 0x06, - 0x5d, 0x8f, 0x66, 0x35, 0x28, 0xc1, 0x90, 0x16, 0x31, 0x61, 0x2a, 0xf8, 0xbf, 0xd2, 0xc7, 0xa1, - 0xc4, 0x99, 0xfc, 0x7a, 0x0c, 0x11, 0x26, 0x10, 0x93, 0x0d, 0x18, 0x13, 0xec, 0x86, 0xb1, 0xd3, - 0x81, 0x7c, 0x76, 0x5a, 0x0b, 0x2a, 0x49, 0x76, 0x3a, 0x23, 0xbb, 0x3f, 0x16, 0x02, 0x30, 0x42, - 0xc4, 0x8e, 0x3e, 0x8f, 0xd2, 0x86, 0x72, 0x88, 0xf1, 0xa3, 0xaf, 0x26, 0xcb, 0x30, 0x84, 0xea, - 0x5f, 0x1c, 0x04, 0x92, 0xde, 0xe2, 0xea, 0x0c, 0x88, 0x12, 0x39, 0xff, 0xfd, 0xcc, 0x80, 0xfc, - 0x5a, 0x12, 0x88, 0xc9, 0x3d, 0x98, 0xb4, 0x0c, 0xcf, 0xbf, 0xd5, 0x66, 0x3a, 0x48, 0xb0, 0x51, - 0xc6, 0x9f, 0x5e, 0x28, 0xb2, 0xd2, 0x2b, 0x2a, 0xa2, 0xc5, 0x99, 0x83, 0xfd, 0xf2, 0x64, 0xac, - 0x08, 0xe3, 0xa4, 0xc8, 0x1b, 0x30, 0xc6, 0x0a, 0x96, 0x5d, 0xd7, 0x71, 0xe5, 0xec, 0xbf, 0x50, - 0x94, 0x2e, 0x47, 0x22, 0x74, 0xa2, 0xf0, 0x27, 0x46, 0xe8, 0xc9, 0x87, 0x81, 0x38, 0x9b, 0x5c, - 0x2b, 0x6d, 0x5c, 0x17, 0x0a, 0x17, 0x1b, 0x2c, 0x5b, 0x9d, 0x81, 0xc5, 0x39, 0xb9, 0x9a, 0xe4, - 0x56, 0xaa, 0x06, 0x66, 0xb4, 0x22, 0x77, 0x80, 0x84, 0x4a, 0x5b, 0xb8, 0x01, 0x66, 0x87, 0x7a, - 0xdf, 0x3e, 0x17, 0x18, 0xb1, 0xeb, 0x29, 0x14, 0x98, 0x81, 0x56, 0xff, 0xd7, 0x25, 0x18, 0x17, - 0x5b, 0x44, 0x08, 0xd6, 0x27, 0x7f, 0x40, 0xd0, 0xd8, 0x01, 0x51, 0x29, 0xfe, 0xcd, 0xf3, 0x0e, - 0xe7, 0x9e, 0x0f, 0xad, 0xc4, 0xf9, 0xb0, 0xdc, 0x2f, 0xa1, 0xee, 0xc7, 0xc3, 0xbf, 0xd5, 0xe0, - 0x8c, 0x52, 0xfb, 0x14, 0x4e, 0x87, 0x46, 0xfc, 0x74, 0x78, 0xa9, 0xcf, 0xf1, 0xe5, 0x1c, 0x0e, - 0x4e, 0x6c, 0x58, 0x9c, 0x71, 0x3f, 0x0d, 0xb0, 0xc9, 0xd9, 0x89, 0x22, 0xa6, 0x85, 0x4b, 0xbe, - 0x18, 0x42, 0x50, 0xa9, 0x15, 0xe3, 0x59, 0xa5, 0xae, 0x3c, 0xeb, 0x3f, 0x0f, 0xc0, 0x4c, 0x6a, - 0xda, 0xd3, 0x7c, 0x44, 0xfb, 0x3a, 0xf1, 0x91, 0xd2, 0xd7, 0x83, 0x8f, 0x0c, 0x14, 0xe2, 0x23, - 0x3d, 0x9f, 0x13, 0xc4, 0x05, 0xd2, 0x32, 0x9b, 0xa2, 0x59, 0xcd, 0x37, 0x5c, 0x7f, 0xc3, 0x6c, - 0x51, 0xc9, 0x71, 0xbe, 0xa9, 0xb7, 0x2d, 0xcb, 0x5a, 0x08, 0xc6, 0xb3, 0x9a, 0xc2, 0x84, 0x19, - 0xd8, 0xf5, 0xff, 0xaf, 0x04, 0x23, 0x8b, 0x86, 0xc7, 0x7b, 0xfa, 0x31, 0x98, 0x90, 0xa8, 0xab, - 0x2d, 0xa3, 0x49, 0xfb, 0x51, 0xad, 0x25, 0xca, 0x55, 0x05, 0x9d, 0xd0, 0x4e, 0xd4, 0x12, 0x8c, - 0x91, 0x23, 0x7b, 0x30, 0xde, 0x8a, 0x24, 0x71, 0xb9, 0xc4, 0xd7, 0xfa, 0xa7, 0xce, 0xb0, 0x09, - 0x15, 0x4c, 0x29, 0x40, 0x95, 0x96, 0xfe, 0x3a, 0x9c, 0xcd, 0xe8, 0x71, 0x0f, 0x4a, 0xc8, 0x63, - 0x30, 0xc2, 0xf4, 0xc8, 0x48, 0xf6, 0x1a, 0x3f, 0xd8, 0x2f, 0x8f, 0xbc, 0x2c, 0x8a, 0x30, 0x80, - 0xe9, 0x1f, 0x60, 0x02, 0x40, 0xb2, 0x4f, 0x3d, 0x18, 0xab, 0x7e, 0x67, 0x10, 0xa0, 0xb2, 0x80, - 0x8e, 0x2f, 0xb6, 0xd2, 0x4b, 0x30, 0xd4, 0xde, 0x36, 0xbc, 0xa0, 0xc5, 0x13, 0x01, 0xab, 0x58, - 0x67, 0x85, 0xf7, 0xf7, 0xcb, 0xb3, 0x15, 0x97, 0x36, 0xa8, 0xed, 0x9b, 0x86, 0xe5, 0x05, 0x8d, - 0x38, 0x0c, 0x45, 0x3b, 0xb6, 0xc3, 0xd8, 0x26, 0xaf, 0x38, 0xad, 0xb6, 0x45, 0x19, 0x94, 0xef, - 0xb0, 0x52, 0xb1, 0x1d, 0xb6, 0x92, 0xc2, 0x84, 0x19, 0xd8, 0x03, 0x9a, 0x55, 0xdb, 0xf4, 0x4d, - 0x23, 0xa4, 0x39, 0x50, 0x9c, 0x66, 0x1c, 0x13, 0x66, 0x60, 0x27, 0x9f, 0xd1, 0x60, 0x2e, 0x5e, - 0x7c, 0xcd, 0xb4, 0x4d, 0x6f, 0x9b, 0x36, 0x38, 0xf1, 0xc1, 0x23, 0x13, 0xbf, 0x74, 0xb0, 0x5f, - 0x9e, 0x5b, 0xc9, 0xc5, 0x88, 0x5d, 0xa8, 0x91, 0xcf, 0x6a, 0xf0, 0x60, 0x62, 0x5e, 0x5c, 0xb3, - 0xd9, 0xa4, 0xae, 0xec, 0xcd, 0xd1, 0x3f, 0xf0, 0xf2, 0xc1, 0x7e, 0xf9, 0xc1, 0x95, 0x7c, 0x94, - 0xd8, 0x8d, 0x9e, 0xfe, 0xab, 0x1a, 0x0c, 0x54, 0xb0, 0x4a, 0x9e, 0x8c, 0x6d, 0xbf, 0x8b, 0xea, - 0xf6, 0xbb, 0xbf, 0x5f, 0x1e, 0xa9, 0x60, 0x55, 0xd9, 0xe8, 0x9f, 0xd5, 0x60, 0xa6, 0xee, 0xd8, - 0xbe, 0xc1, 0xfa, 0x85, 0x42, 0x0e, 0x0d, 0xce, 0xbc, 0x42, 0xda, 0x65, 0x25, 0x81, 0x2c, 0x32, - 0x8a, 0x26, 0x21, 0x1e, 0xa6, 0x29, 0xeb, 0x5f, 0xd5, 0x60, 0xa2, 0x62, 0x39, 0x9d, 0xc6, 0xba, - 0xeb, 0x6c, 0x99, 0x16, 0x7d, 0x67, 0xa8, 0xd4, 0x6a, 0x8f, 0xf3, 0x44, 0x26, 0xae, 0xe2, 0xaa, - 0x15, 0xdf, 0x21, 0x2a, 0xae, 0xda, 0xe5, 0x1c, 0x29, 0xe6, 0xdb, 0xe1, 0xbc, 0x5a, 0x2b, 0x32, - 0x3b, 0x5d, 0x86, 0xc1, 0x3b, 0xa6, 0xdd, 0x48, 0x72, 0xc2, 0x9b, 0xa6, 0xdd, 0x40, 0x0e, 0x09, - 0x79, 0x65, 0x29, 0x97, 0x57, 0xfe, 0xc5, 0x48, 0x7c, 0xda, 0xb8, 0x90, 0xf4, 0x38, 0x8c, 0xd6, - 0x8d, 0xc5, 0x8e, 0xdd, 0xb0, 0x42, 0x36, 0xcb, 0xa6, 0xa0, 0xb2, 0x20, 0xca, 0x30, 0x84, 0x92, - 0x7b, 0x00, 0x91, 0x85, 0xb7, 0x9f, 0xc3, 0x27, 0x32, 0x1e, 0xd7, 0xa8, 0xef, 0x9b, 0x76, 0xd3, - 0x8b, 0xf6, 0x55, 0x04, 0x43, 0x85, 0x1a, 0xf9, 0x18, 0x4c, 0xaa, 0x27, 0xa1, 0x30, 0x35, 0x15, - 0x5c, 0x86, 0xd8, 0x91, 0x7b, 0x5e, 0x12, 0x9e, 0x54, 0x4b, 0x3d, 0x8c, 0x53, 0x23, 0x7b, 0xe1, - 0xb9, 0x2f, 0x0c, 0x5d, 0x83, 0xc5, 0x25, 0x59, 0xf5, 0xc8, 0x3d, 0x27, 0x89, 0x4f, 0xc4, 0x0c, - 0x6f, 0x31, 0x52, 0x19, 0x56, 0x80, 0xa1, 0x93, 0xb2, 0x02, 0x50, 0x18, 0x11, 0x76, 0x10, 0x6f, - 0x76, 0x98, 0x0f, 0xf0, 0x6a, 0x91, 0x01, 0x0a, 0x93, 0x4a, 0x74, 0x65, 0x21, 0x7e, 0x7b, 0x18, - 0xe0, 0x26, 0x3b, 0x30, 0xc1, 0x04, 0xba, 0x1a, 0xb5, 0x68, 0xdd, 0x77, 0xdc, 0xd9, 0x91, 0xe2, - 0x57, 0x02, 0x35, 0x05, 0x8f, 0x90, 0x9e, 0xd4, 0x12, 0x8c, 0xd1, 0x09, 0xcd, 0x44, 0xa3, 0xb9, - 0x66, 0xa2, 0x0e, 0x8c, 0xef, 0x28, 0xe6, 0xcc, 0x31, 0x3e, 0x09, 0x2f, 0x16, 0xe9, 0x58, 0x64, - 0xdb, 0x5c, 0x3c, 0x2b, 0x09, 0x8d, 0xab, 0x76, 0x50, 0x95, 0x0e, 0xd9, 0x84, 0x91, 0x4d, 0x21, - 0xfb, 0xcc, 0x02, 0x9f, 0x8b, 0xe7, 0xfb, 0x10, 0xe9, 0x84, 0x7c, 0x25, 0x7f, 0x60, 0x80, 0x58, - 0xff, 0x89, 0x09, 0x98, 0xa9, 0x58, 0x1d, 0xcf, 0xa7, 0xee, 0x82, 0xbc, 0x13, 0xa7, 0x2e, 0xf9, - 0xa4, 0x06, 0x17, 0xf8, 0xbf, 0x4b, 0xce, 0x5d, 0x7b, 0x89, 0x5a, 0xc6, 0xde, 0xc2, 0x16, 0xab, - 0xd1, 0x68, 0x1c, 0x8d, 0x85, 0x2e, 0x75, 0xa4, 0x92, 0xc2, 0x6d, 0xbf, 0xb5, 0x4c, 0x8c, 0x98, - 0x43, 0x89, 0xfc, 0xa0, 0x06, 0x0f, 0x64, 0x80, 0x96, 0xa8, 0x45, 0xfd, 0x40, 0xf4, 0x3a, 0x6a, - 0x3f, 0x1e, 0x3e, 0xd8, 0x2f, 0x3f, 0x50, 0xcb, 0x43, 0x8a, 0xf9, 0xf4, 0xc8, 0x0f, 0x6b, 0x30, - 0x97, 0x01, 0xbd, 0x66, 0x98, 0x56, 0xc7, 0x0d, 0xa4, 0xb2, 0xa3, 0x76, 0x87, 0x0b, 0x47, 0xb5, - 0x5c, 0xac, 0xd8, 0x85, 0x22, 0xf9, 0x38, 0x9c, 0x0f, 0xa1, 0xb7, 0x6d, 0x9b, 0xd2, 0x46, 0x4c, - 0x46, 0x3b, 0x6a, 0x57, 0x1e, 0x38, 0xd8, 0x2f, 0x9f, 0xaf, 0x65, 0x21, 0xc4, 0x6c, 0x3a, 0xa4, - 0x09, 0x0f, 0x47, 0x00, 0xdf, 0xb4, 0xcc, 0x7b, 0x42, 0x8c, 0xdc, 0x76, 0xa9, 0xb7, 0xed, 0x58, - 0x0d, 0xce, 0x90, 0xb4, 0xc5, 0x77, 0x1f, 0xec, 0x97, 0x1f, 0xae, 0x75, 0xab, 0x88, 0xdd, 0xf1, - 0x90, 0x06, 0x4c, 0x78, 0x75, 0xc3, 0xae, 0xda, 0x3e, 0x75, 0x77, 0x0c, 0x6b, 0x76, 0xb8, 0xd0, - 0x00, 0x05, 0x1b, 0x50, 0xf0, 0x60, 0x0c, 0x2b, 0xf9, 0x20, 0x8c, 0xd2, 0xdd, 0xb6, 0x61, 0x37, - 0xa8, 0x60, 0x3d, 0x63, 0x8b, 0x0f, 0xb1, 0x03, 0x6f, 0x59, 0x96, 0xdd, 0xdf, 0x2f, 0x4f, 0x04, - 0xff, 0xaf, 0x3a, 0x0d, 0x8a, 0x61, 0x6d, 0xf2, 0x51, 0x38, 0xc7, 0x2f, 0xed, 0x1b, 0x94, 0x33, - 0x52, 0x2f, 0x90, 0xd4, 0x47, 0x0b, 0xf5, 0x93, 0x5f, 0xe8, 0xad, 0x66, 0xe0, 0xc3, 0x4c, 0x2a, - 0x6c, 0x19, 0x5a, 0xc6, 0xee, 0x75, 0xd7, 0xa8, 0xd3, 0xad, 0x8e, 0xb5, 0x41, 0xdd, 0x96, 0x69, - 0x0b, 0x55, 0x95, 0xd6, 0x1d, 0xbb, 0xc1, 0xd8, 0x95, 0xf6, 0xf8, 0x90, 0x58, 0x86, 0xd5, 0x6e, - 0x15, 0xb1, 0x3b, 0x1e, 0xf2, 0x0c, 0x4c, 0x98, 0x4d, 0xdb, 0x71, 0xe9, 0x86, 0x61, 0xda, 0xbe, - 0x37, 0x0b, 0xfc, 0x56, 0x87, 0x4f, 0x6b, 0x55, 0x29, 0xc7, 0x58, 0x2d, 0xb2, 0x03, 0xc4, 0xa6, - 0x77, 0xd7, 0x9d, 0x06, 0xdf, 0x02, 0xb7, 0xdb, 0x7c, 0x23, 0xcf, 0x8e, 0x17, 0x9a, 0x1a, 0xae, - 0xc8, 0xac, 0xa5, 0xb0, 0x61, 0x06, 0x05, 0x72, 0x0d, 0x48, 0xcb, 0xd8, 0x5d, 0x6e, 0xb5, 0xfd, - 0xbd, 0xc5, 0x8e, 0x75, 0x47, 0x72, 0x8d, 0x09, 0x3e, 0x17, 0x42, 0xcd, 0x4f, 0x41, 0x31, 0xa3, - 0x05, 0x31, 0xe0, 0x41, 0x31, 0x9e, 0x25, 0x83, 0xb6, 0x1c, 0xdb, 0xa3, 0xbe, 0xa7, 0x6c, 0xd2, - 0xd9, 0x49, 0x7e, 0x75, 0xcb, 0xd5, 0x8a, 0x6a, 0x7e, 0x35, 0xec, 0x86, 0x23, 0xee, 0xbc, 0x32, - 0x75, 0x88, 0xf3, 0xca, 0xb3, 0x30, 0xe9, 0xf9, 0x86, 0xeb, 0x77, 0xda, 0x72, 0x19, 0xce, 0xf0, - 0x65, 0xe0, 0x56, 0xa0, 0x9a, 0x0a, 0xc0, 0x78, 0x3d, 0xb6, 0x7c, 0xc2, 0xd4, 0x27, 0xdb, 0x4d, - 0x47, 0xcb, 0x57, 0x53, 0xca, 0x31, 0x56, 0x4b, 0xff, 0x1f, 0x83, 0x30, 0x9b, 0x3a, 0x1f, 0x02, - 0x87, 0x8f, 0x43, 0x39, 0x80, 0x76, 0x4c, 0x1c, 0xa0, 0x0d, 0x97, 0xc3, 0x0a, 0xd7, 0xdb, 0x9d, - 0x4c, 0x5a, 0x25, 0x4e, 0xeb, 0xd1, 0x83, 0xfd, 0xf2, 0xe5, 0xda, 0x21, 0x75, 0xf1, 0x50, 0x6c, - 0xf9, 0xdc, 0x75, 0xe0, 0x94, 0xb8, 0xeb, 0x47, 0xe1, 0x9c, 0x02, 0x70, 0xa9, 0xd1, 0xd8, 0xeb, - 0x83, 0xbb, 0x73, 0xa6, 0x52, 0xcb, 0xc0, 0x87, 0x99, 0x54, 0x72, 0x59, 0xda, 0xd0, 0x69, 0xb0, - 0x34, 0x7d, 0x7f, 0x00, 0xc6, 0x2a, 0x8e, 0xdd, 0x30, 0xf9, 0xe7, 0xf1, 0x54, 0xec, 0x1a, 0xef, - 0x61, 0x55, 0x3e, 0xbb, 0xbf, 0x5f, 0x9e, 0x0c, 0x2b, 0x2a, 0x02, 0xdb, 0x73, 0xa1, 0xed, 0x5c, - 0x68, 0x3d, 0xef, 0x8e, 0x1b, 0xbd, 0xef, 0xef, 0x97, 0xcf, 0x84, 0xcd, 0xe2, 0x76, 0x70, 0xc6, - 0xaf, 0x2c, 0xc3, 0xf3, 0x37, 0x5c, 0xc3, 0xf6, 0xcc, 0x3e, 0x8c, 0x2e, 0xa1, 0xb1, 0x73, 0x25, - 0x85, 0x0d, 0x33, 0x28, 0x90, 0x37, 0x60, 0x8a, 0x95, 0xde, 0x6e, 0x37, 0x0c, 0x9f, 0x16, 0xb4, - 0xb5, 0x84, 0xbe, 0x06, 0x2b, 0x31, 0x4c, 0x98, 0xc0, 0x2c, 0xae, 0x3d, 0x0d, 0xcf, 0xb1, 0xf9, - 0x7a, 0xc6, 0xae, 0x3d, 0x59, 0x29, 0x4a, 0x28, 0x79, 0x02, 0x46, 0x5a, 0xd4, 0xf3, 0x8c, 0x26, - 0xe5, 0x67, 0xee, 0x58, 0x24, 0xbc, 0xaf, 0x8a, 0x62, 0x0c, 0xe0, 0xe4, 0xbd, 0x30, 0x54, 0x77, - 0x1a, 0xd4, 0x9b, 0x1d, 0xe1, 0x6c, 0x85, 0x71, 0xd8, 0xa1, 0x0a, 0x2b, 0xb8, 0xbf, 0x5f, 0x1e, - 0xe3, 0xa6, 0x61, 0xf6, 0x0b, 0x45, 0x25, 0xfd, 0x27, 0x99, 0xa2, 0x9e, 0xb0, 0x4c, 0xf4, 0x70, - 0x5d, 0x7b, 0x7a, 0x37, 0x9f, 0xfa, 0xe7, 0x34, 0x98, 0x60, 0x3d, 0x74, 0x1d, 0x6b, 0xdd, 0x32, - 0x6c, 0x4a, 0xbe, 0x5f, 0x83, 0xe9, 0x6d, 0xb3, 0xb9, 0xad, 0xfa, 0x5b, 0x48, 0x61, 0xb8, 0x90, - 0x41, 0xe3, 0x46, 0x02, 0xd7, 0xe2, 0xb9, 0x83, 0xfd, 0xf2, 0x74, 0xb2, 0x14, 0x53, 0x34, 0xf5, - 0x4f, 0x97, 0xe0, 0x9c, 0xec, 0x99, 0xc5, 0xa4, 0xd3, 0xb6, 0xe5, 0xec, 0xb5, 0xa8, 0x7d, 0x1a, - 0xae, 0x11, 0xc1, 0x0a, 0x95, 0x72, 0x57, 0xa8, 0x95, 0x5a, 0xa1, 0x81, 0x22, 0x2b, 0x14, 0x6e, - 0xe4, 0x43, 0x56, 0xe9, 0x4f, 0x34, 0x98, 0xcd, 0x9a, 0x8b, 0x53, 0x30, 0xfc, 0xb4, 0xe2, 0x86, - 0x9f, 0x1b, 0x45, 0x2d, 0x79, 0xc9, 0xae, 0xe7, 0x18, 0x80, 0xfe, 0xb8, 0x04, 0x17, 0xa2, 0xea, - 0x55, 0xdb, 0xf3, 0x0d, 0xcb, 0x12, 0xe2, 0xc3, 0xc9, 0xaf, 0x7b, 0x3b, 0x66, 0xbf, 0x5b, 0xeb, - 0x6f, 0xa8, 0x6a, 0xdf, 0x73, 0x2f, 0x3f, 0x77, 0x13, 0x97, 0x9f, 0xeb, 0xc7, 0x48, 0xb3, 0xfb, - 0x3d, 0xe8, 0x7f, 0xd5, 0x60, 0x2e, 0xbb, 0xe1, 0x29, 0x6c, 0x2a, 0x27, 0xbe, 0xa9, 0x3e, 0x7c, - 0x7c, 0xa3, 0xce, 0xd9, 0x56, 0xbf, 0x50, 0xca, 0x1b, 0x2d, 0x37, 0x02, 0x6e, 0xc1, 0x19, 0x97, - 0x36, 0x4d, 0xcf, 0x97, 0xb7, 0x74, 0x47, 0x73, 0xaa, 0x0b, 0x0c, 0xe3, 0x67, 0x30, 0x8e, 0x03, - 0x93, 0x48, 0xc9, 0x1a, 0x8c, 0x78, 0x94, 0x36, 0x18, 0xfe, 0x52, 0xef, 0xf8, 0xc3, 0xd3, 0xa8, - 0x26, 0xda, 0x62, 0x80, 0x84, 0x7c, 0x07, 0x4c, 0x36, 0xc2, 0x2f, 0xea, 0x10, 0xdf, 0x95, 0x24, - 0x56, 0x2e, 0x49, 0x2f, 0xa9, 0xad, 0x31, 0x8e, 0x4c, 0xff, 0x4b, 0x0d, 0x1e, 0xea, 0xb6, 0xb7, - 0xc8, 0x9b, 0x00, 0xf5, 0x40, 0xbc, 0x10, 0x3e, 0x95, 0x05, 0x6f, 0x5c, 0x43, 0x21, 0x25, 0xfa, - 0x40, 0xc3, 0x22, 0x0f, 0x15, 0x22, 0x19, 0x2e, 0x31, 0xa5, 0x13, 0x72, 0x89, 0xd1, 0xff, 0x9b, - 0xa6, 0xb2, 0x22, 0x75, 0x6d, 0xdf, 0x69, 0xac, 0x48, 0xed, 0x7b, 0xee, 0xa5, 0xc2, 0xef, 0x96, - 0xe0, 0x72, 0x76, 0x13, 0xe5, 0xec, 0xfd, 0x10, 0x0c, 0xb7, 0x85, 0xe3, 0xeb, 0x00, 0x3f, 0x1b, - 0x1f, 0x67, 0x9c, 0x45, 0xb8, 0xa5, 0xde, 0xdf, 0x2f, 0xcf, 0x65, 0x31, 0x7a, 0xe9, 0xd0, 0x2a, - 0xdb, 0x11, 0x33, 0x61, 0xfd, 0x14, 0xd2, 0xdf, 0xb7, 0xf4, 0xc8, 0x5c, 0x8c, 0x4d, 0x6a, 0xf5, - 0x6c, 0xf0, 0xfc, 0x84, 0x06, 0x53, 0xb1, 0x1d, 0xed, 0xcd, 0x0e, 0xf1, 0x3d, 0x5a, 0xc8, 0x1b, - 0x21, 0xf6, 0xa9, 0x44, 0x27, 0x77, 0xac, 0xd8, 0xc3, 0x04, 0xc1, 0x04, 0x9b, 0x55, 0x67, 0xf5, - 0x1d, 0xc7, 0x66, 0xd5, 0xce, 0xe7, 0xb0, 0xd9, 0x1f, 0x2f, 0xe5, 0x8d, 0x96, 0xb3, 0xd9, 0xbb, - 0x30, 0x16, 0x3c, 0xe1, 0x09, 0xd8, 0xc5, 0xb5, 0x7e, 0xfb, 0x24, 0xd0, 0x45, 0x9e, 0x78, 0x41, - 0x89, 0x87, 0x11, 0x2d, 0xf2, 0xbd, 0x1a, 0x40, 0xb4, 0x30, 0xf2, 0xa3, 0xda, 0x38, 0xbe, 0xe9, - 0x50, 0xc4, 0x9a, 0x29, 0xf6, 0x49, 0x2b, 0x9b, 0x42, 0xa1, 0xab, 0xff, 0xc5, 0x00, 0x90, 0x74, - 0xdf, 0x7b, 0xbb, 0xdb, 0x3a, 0x44, 0x20, 0x7d, 0x01, 0xce, 0x34, 0x2d, 0x67, 0xd3, 0xb0, 0xac, - 0x3d, 0xf9, 0x46, 0x42, 0x7a, 0xdb, 0x9f, 0x65, 0x07, 0xd3, 0xf5, 0x38, 0x08, 0x93, 0x75, 0x49, - 0x1b, 0xa6, 0x5d, 0x5a, 0x77, 0xec, 0xba, 0x69, 0x71, 0xd5, 0xc9, 0xe9, 0xf8, 0x05, 0x35, 0x70, - 0x2e, 0xde, 0x63, 0x02, 0x17, 0xa6, 0xb0, 0x93, 0xc7, 0x60, 0xa4, 0xed, 0x9a, 0x2d, 0xc3, 0xdd, - 0xe3, 0xca, 0xd9, 0xa8, 0xb0, 0xdb, 0xaf, 0x8b, 0x22, 0x0c, 0x60, 0xe4, 0xa3, 0x30, 0x66, 0x99, - 0x5b, 0xb4, 0xbe, 0x57, 0xb7, 0xa8, 0x34, 0x88, 0xde, 0x3a, 0x9e, 0x2d, 0xb3, 0x12, 0xa0, 0x95, - 0x5e, 0x3e, 0xc1, 0x4f, 0x8c, 0x08, 0x92, 0x2a, 0x9c, 0xbd, 0xeb, 0xb8, 0x77, 0xa8, 0x6b, 0x51, - 0xcf, 0xab, 0x75, 0xda, 0x6d, 0xc7, 0xf5, 0x69, 0x83, 0x9b, 0x4d, 0x47, 0xc5, 0x43, 0x90, 0x57, - 0xd2, 0x60, 0xcc, 0x6a, 0xa3, 0x7f, 0xa6, 0x04, 0x0f, 0x76, 0xe9, 0x04, 0x41, 0xf6, 0x6d, 0xc8, - 0x39, 0x92, 0x3b, 0xe1, 0x19, 0xb1, 0x9f, 0x65, 0xe1, 0xfd, 0xfd, 0xf2, 0x23, 0x5d, 0x10, 0xd4, - 0xd8, 0x56, 0xa4, 0xcd, 0x3d, 0x8c, 0xd0, 0x90, 0x2a, 0x0c, 0x37, 0xa2, 0x5b, 0x84, 0xb1, 0xc5, - 0xa7, 0x18, 0xb7, 0x16, 0xf6, 0xbe, 0x5e, 0xb1, 0x49, 0x04, 0x64, 0x05, 0x46, 0x84, 0x6f, 0x10, - 0x95, 0x9c, 0xff, 0x69, 0xae, 0x1e, 0x8b, 0xa2, 0x5e, 0x91, 0x05, 0x28, 0xf4, 0x3f, 0xd7, 0x60, - 0xa4, 0xe2, 0xb8, 0x74, 0x69, 0xad, 0x46, 0xf6, 0x60, 0x5c, 0x79, 0xa5, 0x28, 0xb9, 0x60, 0x41, - 0xb6, 0xc0, 0x31, 0x2e, 0x44, 0xd8, 0x82, 0x77, 0x15, 0x61, 0x01, 0xaa, 0xb4, 0xc8, 0x9b, 0x6c, - 0xce, 0xef, 0xba, 0xa6, 0xcf, 0x08, 0xf7, 0x73, 0x69, 0x2f, 0x08, 0x63, 0x80, 0x4b, 0xec, 0xa8, - 0xf0, 0x27, 0x46, 0x54, 0xf4, 0x75, 0xc6, 0x01, 0x92, 0xdd, 0x24, 0x57, 0x61, 0xb0, 0xe5, 0x34, - 0x82, 0x75, 0x7f, 0x4f, 0xf0, 0x7d, 0xaf, 0x3a, 0x0d, 0x36, 0xb7, 0x17, 0xd2, 0x2d, 0xb8, 0x65, - 0x9e, 0xb7, 0xd1, 0xd7, 0x60, 0x3a, 0x49, 0x9f, 0x5c, 0x85, 0xa9, 0xba, 0xd3, 0x6a, 0x39, 0x76, - 0xad, 0xb3, 0xb5, 0x65, 0xee, 0xd2, 0xd8, 0x83, 0x97, 0x4a, 0x0c, 0x82, 0x89, 0x9a, 0xfa, 0x17, - 0x34, 0x18, 0x60, 0xeb, 0xa2, 0xc3, 0x70, 0xc3, 0x69, 0x19, 0xa6, 0x2d, 0x7b, 0xc5, 0x1f, 0xf7, - 0x2c, 0xf1, 0x12, 0x94, 0x10, 0xd2, 0x86, 0xb1, 0x40, 0x68, 0xea, 0xcb, 0xbd, 0x71, 0x69, 0xad, - 0x16, 0xba, 0x84, 0x87, 0x9c, 0x3c, 0x28, 0xf1, 0x30, 0x22, 0xa2, 0x1b, 0x30, 0xb3, 0xb4, 0x56, - 0xab, 0xda, 0x75, 0xab, 0xd3, 0xa0, 0xcb, 0xbb, 0xfc, 0x0f, 0xe3, 0x25, 0xa6, 0x28, 0x91, 0xe3, - 0xe4, 0xbc, 0x44, 0x56, 0xc2, 0x00, 0xc6, 0xaa, 0x51, 0xd1, 0x42, 0xbe, 0xff, 0xe0, 0xd5, 0x24, - 0x12, 0x0c, 0x60, 0xfa, 0x57, 0x4b, 0x30, 0xae, 0x74, 0x88, 0x58, 0x30, 0x22, 0x86, 0xeb, 0xf5, - 0xf3, 0xc6, 0x2f, 0xd5, 0x6b, 0x41, 0x5d, 0x4c, 0xa8, 0x87, 0x01, 0x09, 0x95, 0x2f, 0x96, 0xba, - 0xf0, 0xc5, 0xf9, 0xd8, 0x33, 0x1a, 0xf1, 0x49, 0x4e, 0xe5, 0x3f, 0xa1, 0x21, 0x0f, 0xc9, 0x13, - 0x44, 0xf8, 0x17, 0x8e, 0x26, 0x4e, 0x8f, 0x2d, 0x18, 0xba, 0xe7, 0xd8, 0xd4, 0x93, 0x76, 0xcf, - 0x63, 0x1a, 0xe0, 0x18, 0x93, 0x0f, 0x5e, 0x63, 0x78, 0x51, 0xa0, 0xd7, 0x7f, 0x4a, 0x03, 0x58, - 0x32, 0x7c, 0x43, 0x5c, 0x05, 0xf7, 0xe0, 0x3d, 0xf7, 0x50, 0xec, 0xe0, 0x1b, 0x4d, 0x3d, 0x6b, - 0x18, 0xf4, 0xcc, 0x7b, 0xc1, 0xf0, 0x43, 0x81, 0x5a, 0x60, 0xaf, 0x99, 0xf7, 0x28, 0x72, 0x38, - 0x79, 0x12, 0xc6, 0xa8, 0x5d, 0x77, 0xf7, 0xda, 0x8c, 0x79, 0x0f, 0xf2, 0x59, 0xe5, 0x5f, 0xe8, - 0x72, 0x50, 0x88, 0x11, 0x5c, 0x7f, 0x0a, 0xe2, 0x5a, 0x51, 0x0f, 0x4e, 0x78, 0x7f, 0xa5, 0xc1, - 0xc5, 0xa5, 0x8e, 0x61, 0x2d, 0xb4, 0xd9, 0x46, 0x35, 0xac, 0x6b, 0x8e, 0xb8, 0x4d, 0x65, 0xaa, - 0xc2, 0x7b, 0x61, 0x34, 0x90, 0x43, 0x24, 0x86, 0x50, 0x62, 0x0b, 0x18, 0x25, 0x86, 0x35, 0x88, - 0x01, 0xa3, 0x5e, 0x20, 0x19, 0x97, 0xfa, 0x90, 0x8c, 0x03, 0x12, 0xa1, 0x64, 0x1c, 0xa2, 0x25, - 0x08, 0x17, 0xe4, 0x07, 0x51, 0xa3, 0xee, 0x8e, 0x59, 0xa7, 0x0b, 0xf5, 0xba, 0xd3, 0xb1, 0x7d, - 0x4f, 0x0a, 0x0c, 0xfc, 0x0a, 0xbb, 0x9a, 0x59, 0x03, 0x73, 0x5a, 0xea, 0x5f, 0x1b, 0x84, 0x07, - 0x96, 0x37, 0x2a, 0x4b, 0x72, 0x42, 0x4d, 0xc7, 0xbe, 0x49, 0xf7, 0xfe, 0xd6, 0x29, 0xf1, 0x6f, - 0x9d, 0x12, 0x8f, 0xd1, 0x29, 0xf1, 0x25, 0x98, 0x8e, 0xb6, 0x97, 0xf4, 0xd8, 0x79, 0x32, 0xa9, - 0x50, 0x8c, 0x05, 0x47, 0x6f, 0x5a, 0x09, 0xd0, 0xef, 0x6b, 0x30, 0xbd, 0xbc, 0xdb, 0x36, 0x5d, - 0xfe, 0xf8, 0x4e, 0xf8, 0xdd, 0x92, 0x27, 0x22, 0xf7, 0x5c, 0x2d, 0x6e, 0xfa, 0x4f, 0xba, 0xe8, - 0x92, 0x2d, 0x98, 0xa2, 0xbc, 0x39, 0x97, 0xf8, 0x0d, 0xbf, 0xc8, 0x0e, 0x14, 0x2f, 0x4e, 0x63, - 0x58, 0x30, 0x81, 0x95, 0xd4, 0x60, 0xaa, 0x6e, 0x19, 0x9e, 0x67, 0x6e, 0x99, 0xf5, 0xc8, 0xad, - 0x7c, 0x6c, 0xf1, 0x49, 0x7e, 0x78, 0xc7, 0x20, 0xf7, 0xf7, 0xcb, 0xe7, 0x65, 0x3f, 0xe3, 0x00, - 0x4c, 0xa0, 0xd0, 0xdf, 0x2e, 0xc1, 0xe4, 0xf2, 0x6e, 0xdb, 0xf1, 0x3a, 0x2e, 0xe5, 0x55, 0x4f, - 0xc1, 0x86, 0xf1, 0x04, 0x8c, 0x6c, 0x1b, 0x76, 0xc3, 0xa2, 0xae, 0xe4, 0xdf, 0xe1, 0xdc, 0xde, - 0x10, 0xc5, 0x18, 0xc0, 0xc9, 0x5b, 0x00, 0x5e, 0x7d, 0x9b, 0x36, 0x3a, 0x5c, 0x06, 0x14, 0x5f, - 0xd9, 0xcd, 0x22, 0xa7, 0x50, 0x6c, 0x8c, 0xb5, 0x10, 0xa5, 0x3c, 0x1b, 0xc3, 0xdf, 0xa8, 0x90, - 0xd3, 0x7f, 0x5f, 0x83, 0x99, 0x58, 0xbb, 0x53, 0x50, 0xcd, 0xb7, 0xe2, 0xaa, 0xf9, 0x42, 0xdf, - 0x63, 0xcd, 0xd1, 0xc8, 0x3f, 0x55, 0x82, 0x8b, 0x39, 0x73, 0x92, 0x72, 0x44, 0xd3, 0x4e, 0xc9, - 0x11, 0xad, 0x03, 0xe3, 0xbe, 0x63, 0xc9, 0xd7, 0x0f, 0xc1, 0x0c, 0x14, 0x72, 0x33, 0xdb, 0x08, - 0xd1, 0x44, 0x6e, 0x66, 0x51, 0x99, 0x87, 0x2a, 0x1d, 0xfd, 0x57, 0x35, 0x18, 0x0b, 0x2d, 0x80, - 0xdf, 0x50, 0xb7, 0x70, 0xbd, 0x3f, 0x92, 0xd7, 0x7f, 0xa3, 0x04, 0x17, 0x42, 0xdc, 0x01, 0x9b, - 0xab, 0xf9, 0x8c, 0x6f, 0x1c, 0x6e, 0x46, 0x78, 0x28, 0xe6, 0x22, 0x3b, 0x9a, 0x7e, 0xa9, 0xd0, - 0xee, 0xb8, 0x6d, 0xc7, 0x0b, 0x04, 0x2a, 0x21, 0x79, 0x8a, 0x22, 0x0c, 0x60, 0x64, 0x0d, 0x86, - 0x3c, 0x46, 0x4f, 0x1e, 0x47, 0x47, 0x9c, 0x0d, 0x2e, 0x13, 0xf2, 0xfe, 0xa2, 0x40, 0x43, 0xde, - 0x52, 0x79, 0xf8, 0x50, 0x71, 0x43, 0x15, 0x1b, 0x49, 0x23, 0x14, 0xa9, 0xd2, 0x4f, 0x34, 0x33, - 0xcf, 0x84, 0x15, 0x98, 0x96, 0x7e, 0x66, 0x62, 0xdb, 0xd8, 0x75, 0x4a, 0x3e, 0x18, 0xdb, 0x19, - 0x8f, 0x26, 0xee, 0xe1, 0xcf, 0x25, 0xeb, 0x47, 0x3b, 0x46, 0xf7, 0x60, 0xf4, 0xba, 0xec, 0x24, - 0x99, 0x83, 0x92, 0x19, 0xac, 0x05, 0x48, 0x1c, 0xa5, 0xea, 0x12, 0x96, 0xcc, 0x1e, 0x5c, 0x95, - 0xd5, 0x63, 0x69, 0xa0, 0xfb, 0xb1, 0xa4, 0xff, 0x51, 0x09, 0xce, 0x05, 0x54, 0x83, 0x31, 0x2e, - 0xc9, 0x5b, 0xcc, 0x43, 0xa4, 0xeb, 0xc3, 0xcd, 0x4a, 0xb7, 0x60, 0x90, 0x33, 0xc0, 0x42, 0xb7, - 0x9b, 0x21, 0x42, 0xd6, 0x1d, 0xe4, 0x88, 0xc8, 0x47, 0x61, 0xd8, 0x62, 0xa2, 0x6a, 0xe0, 0x43, - 0x5c, 0xc8, 0x08, 0x97, 0x35, 0x5c, 0x21, 0x01, 0xcb, 0xf8, 0x24, 0xe1, 0xa5, 0x97, 0x28, 0x44, - 0x49, 0x73, 0xee, 0x39, 0x18, 0x57, 0xaa, 0x1d, 0x29, 0x38, 0xc9, 0x17, 0x4a, 0x30, 0x7b, 0x83, - 0x5a, 0xad, 0xcc, 0x2b, 0xe9, 0x32, 0x0c, 0xd5, 0xb7, 0x0d, 0x57, 0xc4, 0xbd, 0x99, 0x10, 0x9b, - 0xbc, 0xc2, 0x0a, 0x50, 0x94, 0x93, 0x4d, 0x18, 0xe6, 0xa8, 0x82, 0xeb, 0x8a, 0x17, 0x95, 0x99, - 0x8c, 0x02, 0x22, 0x7d, 0x57, 0x18, 0x31, 0x29, 0x1a, 0x78, 0xac, 0x02, 0x3b, 0x5e, 0x3e, 0x5c, - 0xbb, 0xb5, 0x26, 0x94, 0xf1, 0x97, 0x39, 0x46, 0x94, 0x98, 0xc9, 0x3d, 0x98, 0x74, 0xea, 0x26, - 0xd2, 0xb6, 0xe3, 0x99, 0xbe, 0xe3, 0xee, 0xc9, 0x45, 0x2b, 0x74, 0xb4, 0xdc, 0xaa, 0x54, 0x23, - 0x44, 0xe2, 0xaa, 0x28, 0x56, 0x84, 0x71, 0x52, 0xfa, 0x97, 0x34, 0x18, 0xbf, 0x61, 0x6e, 0x52, - 0x57, 0xb8, 0xd2, 0x71, 0x55, 0x3b, 0x16, 0xc1, 0x65, 0x3c, 0x2b, 0x7a, 0x0b, 0xd9, 0x85, 0x31, - 0x79, 0x0e, 0x87, 0x4f, 0x45, 0xae, 0x17, 0x73, 0x32, 0x08, 0x49, 0xcb, 0xf3, 0x4d, 0x7d, 0x9b, - 0x1d, 0x50, 0xc0, 0x88, 0x98, 0xfe, 0x16, 0x9c, 0xcd, 0x68, 0xc4, 0x16, 0x92, 0x7b, 0x93, 0xc9, - 0x8f, 0x26, 0xe0, 0x56, 0x6c, 0x21, 0x79, 0x39, 0x79, 0x00, 0x06, 0xa8, 0xdd, 0x90, 0x5f, 0xcc, - 0xc8, 0xc1, 0x7e, 0x79, 0x60, 0xd9, 0x6e, 0x20, 0x2b, 0x63, 0x4c, 0xdc, 0x72, 0x62, 0x12, 0x1b, - 0x67, 0xe2, 0x2b, 0xb2, 0x0c, 0x43, 0x28, 0x77, 0x0b, 0x49, 0x7a, 0x40, 0x30, 0xe1, 0x7f, 0x7a, - 0x2b, 0xc1, 0x5b, 0xfa, 0x71, 0xbc, 0x48, 0xf2, 0xa9, 0xc5, 0x59, 0x39, 0x21, 0x29, 0x8e, 0x87, - 0x29, 0xba, 0xfa, 0x2f, 0x0f, 0xc2, 0xc3, 0x37, 0x1c, 0xd7, 0xbc, 0xe7, 0xd8, 0xbe, 0x61, 0xad, - 0x3b, 0x8d, 0xc8, 0x29, 0x4e, 0x1e, 0x59, 0xdf, 0xa7, 0xc1, 0xc5, 0x7a, 0xbb, 0x23, 0x94, 0x87, - 0xc0, 0xaf, 0x6c, 0x9d, 0xba, 0xa6, 0x53, 0xd4, 0x77, 0x9a, 0x47, 0xe3, 0xa8, 0xac, 0xdf, 0xce, - 0x42, 0x89, 0x79, 0xb4, 0xb8, 0x0b, 0x77, 0xc3, 0xb9, 0x6b, 0xf3, 0xce, 0xd5, 0x7c, 0x3e, 0x9b, - 0xf7, 0xa2, 0x45, 0x28, 0xe8, 0xc2, 0xbd, 0x94, 0x89, 0x11, 0x73, 0x28, 0x91, 0x8f, 0xc3, 0x79, - 0x53, 0x74, 0x0e, 0xa9, 0xd1, 0x30, 0x6d, 0xea, 0x79, 0xc2, 0xff, 0xb3, 0x0f, 0x1f, 0xe5, 0x6a, - 0x16, 0x42, 0xcc, 0xa6, 0x43, 0x5e, 0x07, 0xf0, 0xf6, 0xec, 0xba, 0x9c, 0xff, 0x62, 0xde, 0x6b, - 0x42, 0x44, 0x0e, 0xb1, 0xa0, 0x82, 0x91, 0x29, 0x5a, 0x7e, 0xb8, 0x29, 0x87, 0xb9, 0x07, 0x22, - 0x57, 0xb4, 0xa2, 0x3d, 0x14, 0xc1, 0xf5, 0x7f, 0xac, 0xc1, 0x88, 0x8c, 0x43, 0x44, 0xde, 0x93, - 0xb0, 0x22, 0x86, 0x9c, 0x39, 0x61, 0x49, 0xdc, 0xe3, 0x57, 0xc9, 0x92, 0xb3, 0x4a, 0x26, 0x59, - 0xc8, 0x0c, 0x25, 0x09, 0x47, 0x6c, 0x3a, 0x76, 0xa5, 0x1c, 0x98, 0xa8, 0x15, 0x62, 0xfa, 0x17, - 0x35, 0x98, 0x49, 0xb5, 0xea, 0x41, 0x9a, 0x3a, 0x45, 0x2f, 0xad, 0xdf, 0x1d, 0x84, 0x29, 0xee, - 0xc0, 0x6d, 0x1b, 0x96, 0x30, 0xf0, 0x9d, 0x82, 0xfa, 0xf6, 0x24, 0x8c, 0x99, 0xad, 0x56, 0xc7, - 0x67, 0xac, 0x5a, 0xde, 0xd1, 0xf0, 0x35, 0xaf, 0x06, 0x85, 0x18, 0xc1, 0x89, 0x2d, 0x05, 0x05, - 0xc1, 0xc4, 0x57, 0x8a, 0xad, 0x9c, 0x3a, 0xc0, 0x79, 0x76, 0xa8, 0x8b, 0xd3, 0x3c, 0x4b, 0x8e, - 0xf8, 0x7e, 0x0d, 0xc0, 0xf3, 0x5d, 0xd3, 0x6e, 0xb2, 0x42, 0x29, 0x4c, 0xe0, 0x31, 0x90, 0xad, - 0x85, 0x48, 0x05, 0xf1, 0x28, 0x36, 0x51, 0x08, 0x40, 0x85, 0x32, 0x59, 0x90, 0x32, 0x94, 0xe0, - 0xf8, 0xef, 0x4b, 0x48, 0x8b, 0x0f, 0xa7, 0x03, 0x2c, 0xca, 0x28, 0x10, 0x91, 0x90, 0x35, 0xf7, - 0x2c, 0x8c, 0x85, 0xf4, 0x0e, 0x93, 0x49, 0x26, 0x14, 0x99, 0x64, 0xee, 0x05, 0x38, 0x93, 0xe8, - 0xee, 0x91, 0x44, 0x9a, 0x7f, 0xaf, 0x01, 0x89, 0x8f, 0xfe, 0x14, 0x14, 0xdf, 0x66, 0x5c, 0xf1, - 0x5d, 0xec, 0x7f, 0xc9, 0x72, 0x34, 0xdf, 0x9f, 0x9b, 0x01, 0x1e, 0xa6, 0x2d, 0x0c, 0x5b, 0x28, - 0x0f, 0x2e, 0x76, 0xce, 0x46, 0x2f, 0xeb, 0xe4, 0x97, 0xdb, 0xc7, 0x39, 0x7b, 0x33, 0x81, 0x2b, - 0x3a, 0x67, 0x93, 0x10, 0x4c, 0xd1, 0x25, 0x9f, 0xd6, 0x60, 0xda, 0x88, 0x87, 0x69, 0x0b, 0x66, - 0xa6, 0x50, 0xc0, 0x8d, 0x44, 0xc8, 0xb7, 0xa8, 0x2f, 0x09, 0x80, 0x87, 0x29, 0xb2, 0xe4, 0x19, - 0x98, 0x30, 0xda, 0xe6, 0x42, 0xa7, 0x61, 0x32, 0xc5, 0x29, 0x88, 0x66, 0xc5, 0x95, 0xf9, 0x85, - 0xf5, 0x6a, 0x58, 0x8e, 0xb1, 0x5a, 0x61, 0x3c, 0x34, 0x39, 0x91, 0x83, 0x7d, 0xc6, 0x43, 0x93, - 0x73, 0x18, 0xc5, 0x43, 0x93, 0x53, 0xa7, 0x12, 0x21, 0x36, 0x80, 0x63, 0x36, 0xea, 0x92, 0xe4, - 0xb0, 0x94, 0xa8, 0x8b, 0x88, 0xb9, 0xd5, 0xa5, 0x8a, 0xa4, 0xc8, 0x4f, 0xbf, 0xe8, 0x37, 0x2a, - 0x14, 0xc8, 0xe7, 0x34, 0x98, 0x94, 0xbc, 0x5b, 0xd2, 0x1c, 0xe1, 0x4b, 0xf4, 0x5a, 0xd1, 0xfd, - 0x92, 0xd8, 0x93, 0xf3, 0xa8, 0x22, 0x17, 0x7c, 0x27, 0x7c, 0x98, 0x19, 0x83, 0x61, 0xbc, 0x1f, - 0xe4, 0xef, 0x69, 0x70, 0xce, 0x8b, 0x19, 0xe3, 0x65, 0x07, 0x47, 0x8b, 0x07, 0x6a, 0xaa, 0x65, - 0xe0, 0x93, 0x8e, 0xf5, 0x19, 0x10, 0xcc, 0xa4, 0xcf, 0xc4, 0xb2, 0x33, 0x77, 0x0d, 0xbf, 0xbe, - 0x5d, 0x31, 0xea, 0xdb, 0xfc, 0x2e, 0x46, 0x3c, 0xd0, 0x29, 0xb8, 0xaf, 0x5f, 0x89, 0xa3, 0x12, - 0x5e, 0x0d, 0x89, 0x42, 0x4c, 0x12, 0x24, 0x0e, 0x8c, 0xba, 0x32, 0x56, 0xa9, 0x7c, 0x59, 0x58, - 0x2c, 0x3c, 0x67, 0x32, 0xf0, 0xa9, 0x10, 0xec, 0x83, 0x5f, 0x18, 0x12, 0x21, 0x4d, 0x78, 0x58, - 0xa8, 0x36, 0x0b, 0xb6, 0x63, 0xef, 0xb5, 0x9c, 0x8e, 0xb7, 0xd0, 0xf1, 0xb7, 0xa9, 0xed, 0x07, - 0x96, 0xdc, 0x71, 0x7e, 0x8c, 0xf2, 0x87, 0x22, 0xcb, 0xdd, 0x2a, 0x62, 0x77, 0x3c, 0xe4, 0x55, - 0x18, 0xa5, 0x3b, 0xd4, 0xf6, 0x37, 0x36, 0x56, 0xf8, 0x5b, 0x9f, 0xa3, 0x4b, 0x7b, 0x7c, 0x08, - 0xcb, 0x12, 0x07, 0x86, 0xd8, 0xc8, 0x1d, 0x18, 0xb1, 0x44, 0xb0, 0x59, 0xfe, 0xe6, 0xa7, 0x20, - 0x53, 0x4c, 0x06, 0xae, 0x15, 0xfa, 0x9f, 0xfc, 0x81, 0x01, 0x05, 0xd2, 0x86, 0xcb, 0x0d, 0xba, - 0x65, 0x74, 0x2c, 0x7f, 0xcd, 0xf1, 0x91, 0xbf, 0xca, 0x08, 0x0d, 0x76, 0xc1, 0xb3, 0xae, 0x29, - 0x1e, 0x53, 0x85, 0xbf, 0x77, 0x59, 0x3a, 0xa4, 0x2e, 0x1e, 0x8a, 0x8d, 0xec, 0xc1, 0x23, 0xb2, - 0x0e, 0x7f, 0x06, 0x52, 0xdf, 0x66, 0xb3, 0x9c, 0x26, 0x7a, 0x86, 0x13, 0xfd, 0x7f, 0x0e, 0xf6, - 0xcb, 0x8f, 0x2c, 0x1d, 0x5e, 0x1d, 0x7b, 0xc1, 0xc9, 0x3d, 0xeb, 0x69, 0xe2, 0x06, 0x63, 0x76, - 0xba, 0xf8, 0x1c, 0x27, 0x6f, 0x43, 0x84, 0xeb, 0x4d, 0xb2, 0x14, 0x53, 0x34, 0xc9, 0xcf, 0x6a, - 0x30, 0xeb, 0xf9, 0x6e, 0xa7, 0xee, 0x77, 0x5c, 0xda, 0x48, 0xec, 0xd0, 0x19, 0xde, 0xa1, 0x42, - 0x02, 0x5c, 0x2d, 0x07, 0x27, 0x7f, 0x60, 0x38, 0x9b, 0x07, 0xc5, 0xdc, 0xbe, 0x90, 0xbf, 0xaf, - 0xc1, 0xc5, 0x38, 0x90, 0xa9, 0xa4, 0xa2, 0x9f, 0xa4, 0xf8, 0x1d, 0x41, 0x2d, 0x1b, 0xa5, 0x50, - 0x40, 0x73, 0x80, 0x98, 0xd7, 0x91, 0xb9, 0x0f, 0x01, 0x49, 0xb3, 0xef, 0xc3, 0xe4, 0xb0, 0x51, - 0x55, 0x0e, 0xfb, 0xfc, 0x10, 0x3c, 0xc8, 0x4e, 0x85, 0x48, 0xfb, 0x58, 0x35, 0x6c, 0xa3, 0xf9, - 0x8d, 0x29, 0xb1, 0x7c, 0x49, 0x83, 0x8b, 0xdb, 0xd9, 0x96, 0x01, 0xa9, 0xff, 0x7c, 0xa4, 0x90, - 0x05, 0xa7, 0x9b, 0xb1, 0x41, 0x30, 0xcc, 0xae, 0x55, 0x30, 0xaf, 0x53, 0xe4, 0x43, 0x30, 0x6d, - 0x3b, 0x0d, 0x5a, 0xa9, 0x2e, 0xe1, 0xaa, 0xe1, 0xdd, 0xa9, 0x05, 0x0e, 0x03, 0x43, 0xe2, 0x7b, - 0x59, 0x4b, 0xc0, 0x30, 0x55, 0x9b, 0xec, 0x00, 0x69, 0x3b, 0x8d, 0xe5, 0x1d, 0x11, 0x14, 0xb9, - 0x3f, 0xf7, 0x38, 0x7e, 0x1d, 0xbc, 0x9e, 0xc2, 0x86, 0x19, 0x14, 0xb8, 0x69, 0x83, 0x75, 0x66, - 0xd5, 0xb1, 0x4d, 0xdf, 0x71, 0xf9, 0x93, 0xd5, 0xbe, 0x34, 0x7c, 0x6e, 0xda, 0x58, 0xcb, 0xc4, - 0x88, 0x39, 0x94, 0xf4, 0xff, 0xae, 0xc1, 0x19, 0xb6, 0x2d, 0xd6, 0x5d, 0x67, 0x77, 0xef, 0x1b, - 0x71, 0x43, 0x3e, 0x21, 0x7d, 0xa7, 0x84, 0x49, 0xee, 0xbc, 0xe2, 0x37, 0x35, 0xc6, 0xfb, 0x1c, - 0xb9, 0x4a, 0xa9, 0x56, 0xc9, 0x81, 0x7c, 0xab, 0xa4, 0xfe, 0xb9, 0x92, 0xd0, 0x1c, 0x02, 0xab, - 0xe0, 0x37, 0xe4, 0x77, 0xf8, 0x2c, 0x4c, 0xb2, 0xb2, 0x55, 0x63, 0x77, 0x7d, 0xe9, 0x65, 0xc7, - 0x0a, 0x5e, 0x00, 0x72, 0x53, 0xed, 0x4d, 0x15, 0x80, 0xf1, 0x7a, 0xe4, 0x2a, 0x8c, 0xb4, 0x45, - 0xfc, 0x13, 0xa9, 0xb3, 0x5e, 0x16, 0x0e, 0x46, 0xbc, 0xe8, 0xfe, 0x7e, 0x79, 0x26, 0xba, 0x21, - 0x0c, 0xa2, 0xb0, 0x04, 0x0d, 0xf4, 0xbf, 0x3e, 0x0b, 0x1c, 0xb9, 0x45, 0xfd, 0x6f, 0xc4, 0x39, - 0x79, 0x0a, 0xc6, 0xeb, 0xed, 0x4e, 0xe5, 0x5a, 0xed, 0x23, 0x1d, 0x87, 0xdb, 0x22, 0x78, 0xec, - 0x70, 0xa6, 0x4a, 0x54, 0xd6, 0x6f, 0x07, 0xc5, 0xa8, 0xd6, 0x61, 0xdc, 0xa1, 0xde, 0xee, 0x48, - 0x7e, 0xbb, 0xae, 0xba, 0xb6, 0x73, 0xee, 0x50, 0x59, 0xbf, 0x1d, 0x83, 0x61, 0xaa, 0x36, 0xf9, - 0x38, 0x4c, 0x50, 0xf9, 0xe1, 0xde, 0x30, 0xdc, 0x86, 0xe4, 0x0b, 0xd5, 0xa2, 0x83, 0x0f, 0xa7, - 0x36, 0xe0, 0x06, 0x42, 0x03, 0x5b, 0x56, 0x48, 0x60, 0x8c, 0x20, 0xf9, 0x76, 0x78, 0x20, 0xf8, - 0xcd, 0x56, 0xd9, 0x69, 0x24, 0x19, 0xc5, 0x90, 0x08, 0x07, 0xb1, 0x9c, 0x57, 0x09, 0xf3, 0xdb, - 0x93, 0x9f, 0xd7, 0xe0, 0x42, 0x08, 0x35, 0x6d, 0xb3, 0xd5, 0x69, 0x21, 0xad, 0x5b, 0x86, 0xd9, - 0x92, 0x7a, 0xd7, 0x2b, 0xc7, 0x36, 0xd0, 0x38, 0x7a, 0xc1, 0xac, 0xb2, 0x61, 0x98, 0xd3, 0x25, - 0xf2, 0x45, 0x0d, 0x2e, 0x07, 0xa0, 0x75, 0x97, 0x7a, 0x5e, 0xc7, 0xa5, 0xd1, 0xfb, 0x53, 0x39, - 0x25, 0x23, 0x85, 0x78, 0x27, 0x17, 0x40, 0x97, 0x0f, 0xc1, 0x8d, 0x87, 0x52, 0x57, 0xb7, 0x4b, - 0xcd, 0xd9, 0xf2, 0xa5, 0xa2, 0x76, 0x52, 0xdb, 0x85, 0x91, 0xc0, 0x18, 0x41, 0xf2, 0x4f, 0x34, - 0xb8, 0xa8, 0x16, 0xa8, 0xbb, 0x45, 0x68, 0x68, 0xaf, 0x1e, 0x5b, 0x67, 0x12, 0xf8, 0x85, 0x84, - 0x95, 0x03, 0xc4, 0xbc, 0x5e, 0x31, 0xb6, 0xdd, 0xe2, 0x1b, 0x53, 0x68, 0x71, 0x43, 0x82, 0x6d, - 0x8b, 0xbd, 0xea, 0x61, 0x00, 0x23, 0xcf, 0xc0, 0x44, 0xdb, 0x69, 0xac, 0x9b, 0x0d, 0x6f, 0xc5, - 0x6c, 0x99, 0x3e, 0xd7, 0xb5, 0x06, 0xc4, 0x74, 0xac, 0x3b, 0x8d, 0xf5, 0xea, 0x92, 0x28, 0xc7, - 0x58, 0x2d, 0x32, 0x0f, 0xb0, 0x65, 0x98, 0x56, 0xed, 0xae, 0xd1, 0xbe, 0x15, 0x84, 0x39, 0xe0, - 0xb6, 0x80, 0x6b, 0x61, 0x29, 0x2a, 0x35, 0xd8, 0xfa, 0x31, 0xbe, 0x83, 0x54, 0x84, 0x71, 0xe4, - 0xea, 0xc9, 0x71, 0xac, 0x5f, 0x80, 0x50, 0x74, 0xf8, 0xa6, 0x42, 0x02, 0x63, 0x04, 0xc9, 0xf7, - 0x69, 0x30, 0xe5, 0xed, 0x79, 0x3e, 0x6d, 0x85, 0x7d, 0x38, 0x73, 0xdc, 0x7d, 0xe0, 0x36, 0xe9, - 0x5a, 0x8c, 0x08, 0x26, 0x88, 0xf2, 0x80, 0x11, 0x2d, 0xa3, 0x49, 0xaf, 0x57, 0x6e, 0x98, 0xcd, - 0xed, 0x30, 0xa2, 0xc0, 0x3a, 0x75, 0xeb, 0xd4, 0xf6, 0xb9, 0x62, 0x33, 0x24, 0x03, 0x46, 0xe4, - 0x57, 0xc3, 0x6e, 0x38, 0xc8, 0xeb, 0x30, 0x27, 0xc1, 0x2b, 0xce, 0xdd, 0x14, 0x85, 0x19, 0x4e, - 0x81, 0xbb, 0xb8, 0x55, 0x73, 0x6b, 0x61, 0x17, 0x0c, 0xa4, 0x0a, 0x67, 0x3d, 0xea, 0xf2, 0x2b, - 0x25, 0x11, 0xe9, 0x6a, 0xbd, 0x63, 0x59, 0x1e, 0x57, 0x2d, 0xa4, 0x7b, 0x7f, 0x2d, 0x0d, 0xc6, - 0xac, 0x36, 0xe4, 0x85, 0xf0, 0x05, 0xe1, 0x1e, 0x2b, 0xf8, 0xc8, 0x7a, 0x6d, 0xf6, 0x2c, 0xef, - 0xdf, 0x59, 0xe5, 0x61, 0x60, 0x00, 0xc2, 0x64, 0x5d, 0x76, 0x9a, 0x07, 0x45, 0x8b, 0x1d, 0xd7, - 0xf3, 0x67, 0xcf, 0xf1, 0xc6, 0xfc, 0x34, 0x47, 0x15, 0x80, 0xf1, 0x7a, 0xe4, 0x2a, 0x4c, 0x79, - 0xb4, 0x5e, 0x77, 0x5a, 0x6d, 0xa9, 0xa7, 0xce, 0x9e, 0xe7, 0xbd, 0x17, 0x2b, 0x18, 0x83, 0x60, - 0xa2, 0x26, 0xd9, 0x83, 0xb3, 0x61, 0xd8, 0xbc, 0x15, 0xa7, 0xb9, 0x6a, 0xec, 0x72, 0xe1, 0xf8, - 0xc2, 0xe1, 0xfc, 0x71, 0x3e, 0xf0, 0xa0, 0x98, 0xff, 0x48, 0xc7, 0xb0, 0x7d, 0xd3, 0xdf, 0x13, - 0xd3, 0x55, 0x49, 0xa3, 0xc3, 0x2c, 0x1a, 0x64, 0x05, 0xce, 0x25, 0x8a, 0xaf, 0x99, 0x16, 0xf5, - 0x66, 0x2f, 0xf2, 0x61, 0x73, 0x63, 0x53, 0x25, 0x03, 0x8e, 0x99, 0xad, 0xc8, 0x2d, 0x38, 0xdf, - 0x76, 0x1d, 0x9f, 0xd6, 0xfd, 0x9b, 0x4c, 0x20, 0xb0, 0xe4, 0x00, 0xbd, 0xd9, 0x59, 0x3e, 0x17, - 0xfc, 0x3a, 0x6d, 0x3d, 0xab, 0x02, 0x66, 0xb7, 0x23, 0x9f, 0xd7, 0xe0, 0x92, 0xe7, 0xbb, 0xd4, - 0x68, 0x99, 0x76, 0xb3, 0xe2, 0xd8, 0x36, 0xe5, 0x8c, 0xa9, 0xda, 0x88, 0x5e, 0xc7, 0x3c, 0x50, - 0xe8, 0x14, 0xd1, 0x0f, 0xf6, 0xcb, 0x97, 0x6a, 0x5d, 0x31, 0xe3, 0x21, 0x94, 0xc9, 0x5b, 0x00, - 0x2d, 0xda, 0x72, 0xdc, 0x3d, 0xc6, 0x91, 0x66, 0xe7, 0x8a, 0xeb, 0xc1, 0xab, 0x21, 0x16, 0xf1, - 0xf9, 0xc7, 0x2e, 0x02, 0x23, 0x20, 0x2a, 0xe4, 0xf4, 0xfd, 0x12, 0x9c, 0xcf, 0x64, 0xf5, 0xec, - 0x0b, 0x10, 0xf5, 0x16, 0x82, 0x04, 0x07, 0xf2, 0xee, 0x8c, 0x7f, 0x01, 0xab, 0x71, 0x10, 0x26, - 0xeb, 0x32, 0x41, 0x8c, 0x7f, 0xa9, 0xd7, 0x6a, 0x51, 0xfb, 0x52, 0x24, 0x88, 0x55, 0x13, 0x30, - 0x4c, 0xd5, 0x26, 0x15, 0x98, 0x91, 0x65, 0x55, 0xa6, 0xcb, 0x78, 0xd7, 0x5c, 0x1a, 0x88, 0xb8, - 0x4c, 0x2b, 0x98, 0xa9, 0x26, 0x81, 0x98, 0xae, 0xcf, 0x46, 0xc1, 0x7e, 0xa8, 0xbd, 0x18, 0x8c, - 0x46, 0xb1, 0x16, 0x07, 0x61, 0xb2, 0x6e, 0xa0, 0x6c, 0xc6, 0xba, 0x30, 0x14, 0x8d, 0x62, 0x2d, - 0x01, 0xc3, 0x54, 0x6d, 0xfd, 0x3f, 0x0c, 0xc2, 0x23, 0x3d, 0x88, 0x47, 0xa4, 0x95, 0x3d, 0xdd, - 0x47, 0xff, 0x70, 0x7b, 0x5b, 0x9e, 0x76, 0xce, 0xf2, 0x1c, 0x9d, 0x5e, 0xaf, 0xcb, 0xe9, 0xe5, - 0x2d, 0xe7, 0xd1, 0x49, 0xf6, 0xbe, 0xfc, 0xad, 0xec, 0xe5, 0x2f, 0x38, 0xab, 0x87, 0x6e, 0x97, - 0x76, 0xce, 0x76, 0x29, 0x38, 0xab, 0x3d, 0x6c, 0xaf, 0x3f, 0x18, 0x84, 0x47, 0x7b, 0x11, 0xd5, - 0x0a, 0xee, 0xaf, 0x0c, 0x96, 0x77, 0xa2, 0xfb, 0x2b, 0xef, 0x01, 0xe2, 0x09, 0xee, 0xaf, 0x0c, - 0x92, 0x27, 0xbd, 0xbf, 0xf2, 0x66, 0xf5, 0xa4, 0xf6, 0x57, 0xde, 0xac, 0xf6, 0xb0, 0xbf, 0xfe, - 0x2c, 0x79, 0x3e, 0x84, 0xf2, 0x62, 0x15, 0x06, 0xea, 0xed, 0x4e, 0x41, 0x26, 0xc5, 0x3d, 0xad, - 0x2a, 0xeb, 0xb7, 0x91, 0xe1, 0x20, 0x08, 0xc3, 0x62, 0xff, 0x14, 0x64, 0x41, 0xdc, 0x7b, 0x4e, - 0x6c, 0x49, 0x94, 0x98, 0xd8, 0x54, 0xd1, 0xf6, 0x36, 0x6d, 0x51, 0xd7, 0xb0, 0x6a, 0xbe, 0xe3, - 0x1a, 0xcd, 0xa2, 0xdc, 0x46, 0x98, 0xe1, 0x13, 0xb8, 0x30, 0x85, 0x9d, 0x4d, 0x48, 0xdb, 0x6c, - 0x14, 0xe4, 0x2f, 0x7c, 0x42, 0xd6, 0xab, 0x4b, 0xc8, 0x70, 0xe8, 0x5f, 0x19, 0x05, 0x25, 0x72, - 0x2c, 0xf9, 0x8c, 0x06, 0x33, 0xf5, 0x64, 0x30, 0xb3, 0x7e, 0x9c, 0x6a, 0x52, 0x91, 0xd1, 0xc4, - 0x96, 0x4f, 0x15, 0x63, 0x9a, 0x2c, 0xf9, 0x1e, 0x4d, 0x58, 0xaa, 0xc2, 0x2b, 0x21, 0x39, 0xad, - 0xd7, 0x8f, 0xe9, 0xf2, 0x34, 0x32, 0x79, 0x45, 0xf7, 0x74, 0x71, 0x82, 0xe4, 0x8b, 0x1a, 0x9c, - 0xbf, 0x93, 0x65, 0x60, 0x97, 0x93, 0x7f, 0xab, 0x68, 0x57, 0x72, 0x2c, 0xf6, 0x42, 0xe2, 0xcc, - 0xac, 0x80, 0xd9, 0x1d, 0x09, 0x67, 0x29, 0xb4, 0x39, 0xca, 0xef, 0xb4, 0xf0, 0x2c, 0x25, 0x8c, - 0x97, 0xd1, 0x2c, 0x85, 0x00, 0x8c, 0x13, 0x24, 0x6d, 0x18, 0xbb, 0x13, 0x18, 0x7a, 0xa5, 0x71, - 0xa7, 0x52, 0x94, 0xba, 0x62, 0x2d, 0x16, 0x4e, 0x43, 0x61, 0x21, 0x46, 0x44, 0xc8, 0x36, 0x8c, - 0xdc, 0x11, 0xbc, 0x42, 0x1a, 0x65, 0x16, 0xfa, 0x56, 0x61, 0x85, 0x6d, 0x40, 0x16, 0x61, 0x80, - 0x5e, 0xf5, 0xa7, 0x1e, 0x3d, 0xe4, 0x99, 0xcf, 0xe7, 0x35, 0x38, 0xbf, 0x43, 0x5d, 0xdf, 0xac, - 0x27, 0xaf, 0x37, 0xc6, 0x8a, 0xab, 0xd9, 0x2f, 0x67, 0x21, 0x14, 0xdb, 0x24, 0x13, 0x84, 0xd9, - 0x5d, 0x60, 0x4a, 0xb7, 0xb0, 0x52, 0xd7, 0x7c, 0xc3, 0x37, 0xeb, 0x1b, 0xce, 0x1d, 0x6a, 0x47, - 0x59, 0xda, 0xb8, 0x79, 0x44, 0x46, 0x69, 0x5c, 0xce, 0xaf, 0x86, 0xdd, 0x70, 0xe8, 0x7f, 0xac, - 0x41, 0xca, 0xd6, 0x4a, 0x7e, 0x44, 0x83, 0x89, 0x2d, 0x6a, 0xf8, 0x1d, 0x97, 0x5e, 0x37, 0xfc, - 0x30, 0x7a, 0xc3, 0xcb, 0xc7, 0x61, 0xe2, 0x9d, 0xbf, 0xa6, 0x20, 0x16, 0xce, 0x0f, 0x61, 0x60, - 0x68, 0x15, 0x84, 0xb1, 0x1e, 0xcc, 0xbd, 0x04, 0x33, 0xa9, 0x86, 0x47, 0xba, 0x76, 0xfb, 0x17, - 0x1a, 0x64, 0xe5, 0x71, 0x24, 0xaf, 0xc3, 0x90, 0xd1, 0x68, 0x84, 0x29, 0x90, 0x9e, 0x2b, 0xe6, - 0x87, 0xd3, 0x50, 0x83, 0x64, 0xf0, 0x9f, 0x28, 0xd0, 0x92, 0x6b, 0x40, 0x8c, 0xd8, 0x3d, 0xe7, - 0x6a, 0xf4, 0xf4, 0x9b, 0x5f, 0x0f, 0x2d, 0xa4, 0xa0, 0x98, 0xd1, 0x42, 0xff, 0x94, 0x06, 0x24, - 0x1d, 0x4a, 0x9c, 0xb8, 0x30, 0x2a, 0xb7, 0x72, 0xb0, 0x4a, 0x4b, 0x05, 0x1f, 0x17, 0xc5, 0x5e, - 0xca, 0x45, 0x4e, 0x5d, 0xb2, 0xc0, 0xc3, 0x90, 0x8e, 0xfe, 0x97, 0x1a, 0x44, 0x69, 0x52, 0xc8, - 0xfb, 0x61, 0xbc, 0x41, 0xbd, 0xba, 0x6b, 0xb6, 0xfd, 0xe8, 0x5d, 0x5d, 0xf8, 0x3e, 0x67, 0x29, - 0x02, 0xa1, 0x5a, 0x8f, 0xe8, 0x30, 0xec, 0x1b, 0xde, 0x9d, 0xea, 0x92, 0xd4, 0xfb, 0xf8, 0x29, - 0xbd, 0xc1, 0x4b, 0x50, 0x42, 0xa2, 0xf0, 0x7b, 0x03, 0x3d, 0x84, 0xdf, 0x23, 0x5b, 0xc7, 0x10, - 0x6b, 0x90, 0x1c, 0x1e, 0x67, 0x50, 0xff, 0x99, 0x12, 0x9c, 0x61, 0x55, 0x56, 0x0d, 0xd3, 0xf6, - 0xa9, 0xcd, 0x5f, 0x91, 0x14, 0x9c, 0x84, 0x26, 0x4c, 0xfa, 0xb1, 0x67, 0x96, 0x47, 0x7f, 0x63, - 0x18, 0x7a, 0x0e, 0xc5, 0x1f, 0x57, 0xc6, 0xf1, 0x92, 0xe7, 0x82, 0x67, 0x3c, 0x42, 0x43, 0x7e, - 0x24, 0xd8, 0xaa, 0xfc, 0x6d, 0xce, 0x7d, 0xf9, 0x66, 0x35, 0xcc, 0xad, 0x13, 0x7b, 0xb1, 0xf3, - 0x2c, 0x4c, 0x4a, 0x87, 0x71, 0x11, 0x47, 0x51, 0x6a, 0xc8, 0xfc, 0x84, 0xb9, 0xa6, 0x02, 0x30, - 0x5e, 0x4f, 0xff, 0x9d, 0x12, 0xc4, 0x33, 0xf8, 0x14, 0x9d, 0xa5, 0x74, 0x10, 0xc9, 0xd2, 0x89, - 0x05, 0x91, 0x7c, 0x2f, 0x4f, 0x7f, 0x27, 0xb2, 0xb7, 0x8a, 0x7b, 0x63, 0x35, 0x69, 0x9d, 0xc8, - 0xbd, 0x1a, 0xd6, 0x88, 0xa6, 0x75, 0xf0, 0xc8, 0xd3, 0xfa, 0x7e, 0xe9, 0x49, 0x3a, 0x14, 0x0b, - 0xe5, 0x19, 0x78, 0x92, 0xce, 0xc4, 0x1a, 0x2a, 0x8f, 0x8e, 0xd6, 0xe0, 0xdd, 0x2b, 0x8e, 0xd1, - 0x58, 0x34, 0x2c, 0xb6, 0xef, 0x5c, 0xe9, 0xa3, 0xe5, 0xf1, 0x13, 0x76, 0xdd, 0x75, 0x7c, 0xa7, - 0xee, 0x58, 0xec, 0xfc, 0x33, 0x2c, 0xcb, 0xb9, 0x9b, 0xce, 0xa8, 0xbb, 0x20, 0x8a, 0x31, 0x80, - 0xeb, 0x5f, 0xd1, 0x60, 0x44, 0xc6, 0xe3, 0xef, 0xe1, 0x91, 0xdc, 0x16, 0x0c, 0x71, 0x2d, 0xa7, - 0x1f, 0xe9, 0xb2, 0xb6, 0xed, 0x38, 0x7e, 0x2c, 0x2b, 0x01, 0x7f, 0x77, 0x21, 0x32, 0x00, 0x09, - 0xf4, 0xdc, 0x39, 0xd1, 0xad, 0x6f, 0x9b, 0x3e, 0xe5, 0x3e, 0x18, 0x72, 0xd7, 0x0a, 0xe7, 0x44, - 0xa5, 0x1c, 0x63, 0xb5, 0xf4, 0x2f, 0x0c, 0xc2, 0x65, 0x89, 0x38, 0x25, 0x72, 0x85, 0x0c, 0x73, - 0x0f, 0xce, 0xca, 0xbd, 0xb2, 0xe4, 0x1a, 0x66, 0x78, 0xbf, 0x5f, 0x4c, 0xdb, 0x95, 0x19, 0xaa, - 0x53, 0xe8, 0x30, 0x8b, 0x86, 0x08, 0x3f, 0xcb, 0x8b, 0x6f, 0x50, 0xc3, 0xf2, 0xb7, 0x03, 0xda, - 0xa5, 0x7e, 0xc2, 0xcf, 0xa6, 0xf1, 0x61, 0x26, 0x15, 0xee, 0x5f, 0x20, 0x01, 0x15, 0x97, 0x1a, - 0xaa, 0x73, 0x43, 0x1f, 0x4f, 0x27, 0x56, 0x33, 0x31, 0x62, 0x0e, 0x25, 0x6e, 0x36, 0x34, 0x76, - 0xb9, 0x15, 0x02, 0xa9, 0xef, 0x9a, 0x3c, 0xbb, 0x44, 0x68, 0x38, 0x5f, 0x8d, 0x83, 0x30, 0x59, - 0x97, 0x5c, 0x85, 0x29, 0xee, 0xaf, 0x11, 0x85, 0xa1, 0x1b, 0x8a, 0x22, 0x9d, 0xac, 0xc5, 0x20, - 0x98, 0xa8, 0xa9, 0x7f, 0xa2, 0x04, 0x13, 0x47, 0xcc, 0xe6, 0xd4, 0x51, 0x0e, 0xd7, 0x3e, 0xde, - 0x2b, 0xa9, 0x54, 0x7b, 0x38, 0x5f, 0xc9, 0xab, 0x30, 0xd5, 0xe1, 0x1c, 0x29, 0x08, 0xa5, 0x23, - 0xf7, 0xff, 0x37, 0xb3, 0x51, 0xde, 0x8e, 0x41, 0xee, 0xef, 0x97, 0xe7, 0x54, 0xf4, 0x71, 0x28, - 0x26, 0xf0, 0xe8, 0x9f, 0x1d, 0x80, 0xb3, 0x19, 0xbd, 0xe1, 0xf7, 0xfa, 0x34, 0x21, 0x02, 0xf4, - 0x73, 0xaf, 0x9f, 0x12, 0x27, 0xc2, 0x7b, 0xfd, 0x24, 0x04, 0x53, 0x74, 0xc9, 0xcb, 0x30, 0x50, - 0x77, 0x4d, 0x39, 0xe1, 0xcf, 0x16, 0x52, 0x60, 0xb1, 0xba, 0x38, 0x2e, 0x29, 0x0e, 0x54, 0xb0, - 0x8a, 0x0c, 0x21, 0x3b, 0xc8, 0x54, 0x76, 0x11, 0x48, 0x15, 0xfc, 0x20, 0x53, 0xb9, 0x8a, 0x87, - 0xf1, 0x7a, 0xe4, 0x55, 0x98, 0x95, 0x9a, 0x45, 0xf0, 0xfa, 0xde, 0xb1, 0x3d, 0x9f, 0x7d, 0xd9, - 0xbe, 0x64, 0xfc, 0xdc, 0xe5, 0xed, 0x66, 0x4e, 0x1d, 0xcc, 0x6d, 0xad, 0xff, 0xe9, 0x00, 0xa8, - 0x49, 0xc8, 0xc8, 0x6a, 0x3f, 0x56, 0x93, 0x68, 0xc4, 0x81, 0xe5, 0x64, 0x15, 0x06, 0x9a, 0xed, - 0x4e, 0x41, 0xb3, 0x49, 0x88, 0xee, 0x3a, 0x43, 0xd7, 0x6c, 0x77, 0xc8, 0xcb, 0xa1, 0x21, 0xa6, - 0x98, 0xa9, 0x24, 0x7c, 0x0d, 0x94, 0x30, 0xc6, 0x04, 0x1f, 0xe2, 0x60, 0xee, 0x87, 0xd8, 0x82, - 0x11, 0x4f, 0x5a, 0x69, 0x86, 0x8a, 0x47, 0x8c, 0x52, 0x66, 0x5a, 0x5a, 0x65, 0x84, 0xfe, 0x18, - 0x18, 0x6d, 0x02, 0x1a, 0x4c, 0x36, 0xed, 0xf0, 0x17, 0xd8, 0x5c, 0x31, 0x1e, 0x15, 0xb2, 0xe9, - 0x6d, 0x5e, 0x82, 0x12, 0x92, 0x3a, 0xa2, 0x46, 0x7a, 0x3a, 0xa2, 0x7e, 0xa0, 0x04, 0x24, 0xdd, - 0x0d, 0xf2, 0x08, 0x0c, 0xf1, 0x08, 0x0e, 0x92, 0x17, 0x85, 0x9a, 0x04, 0x7f, 0xc3, 0x8f, 0x02, - 0x46, 0x6a, 0x32, 0xfe, 0x4d, 0xb1, 0xe5, 0xe4, 0x8e, 0x31, 0x92, 0x9e, 0x12, 0x2c, 0xe7, 0x72, - 0xec, 0x41, 0x4b, 0xd6, 0x99, 0x7f, 0x1b, 0x46, 0x5a, 0xa6, 0xcd, 0xef, 0x0a, 0x8b, 0x19, 0xaf, - 0xc4, 0xfd, 0xbd, 0x40, 0x81, 0x01, 0x2e, 0xfd, 0x0f, 0x4a, 0x6c, 0xeb, 0x47, 0x12, 0xf4, 0x1e, - 0x80, 0xd1, 0xf1, 0x1d, 0xc1, 0xc0, 0xe4, 0x17, 0x50, 0x2d, 0xb6, 0xca, 0x21, 0xd2, 0x85, 0x10, - 0xa1, 0xb8, 0xe5, 0x8a, 0x7e, 0xa3, 0x42, 0x8c, 0x91, 0xf6, 0xcd, 0x16, 0x7d, 0xc5, 0xb4, 0x1b, - 0xce, 0x5d, 0x39, 0xbd, 0xfd, 0x92, 0xde, 0x08, 0x11, 0x0a, 0xd2, 0xd1, 0x6f, 0x54, 0x88, 0x31, - 0xd6, 0xc2, 0x15, 0x71, 0x9b, 0xa7, 0xa7, 0x92, 0x7d, 0x73, 0x2c, 0x2b, 0x38, 0x95, 0x47, 0x05, - 0x6b, 0xa9, 0xe4, 0xd4, 0xc1, 0xdc, 0xd6, 0xfa, 0xcf, 0x6b, 0x70, 0x3e, 0x73, 0x2a, 0xc8, 0x75, - 0x98, 0x89, 0x7c, 0xa9, 0x54, 0x66, 0x3f, 0x1a, 0xe5, 0x5c, 0xbb, 0x99, 0xac, 0x80, 0xe9, 0x36, - 0xa4, 0x1a, 0x8a, 0x52, 0xea, 0x61, 0x22, 0x1d, 0xb1, 0x54, 0xd1, 0x48, 0x05, 0x63, 0x56, 0x1b, - 0xfd, 0xdb, 0x63, 0x9d, 0x8d, 0x26, 0x8b, 0x7d, 0x19, 0x9b, 0xb4, 0x19, 0x3e, 0x28, 0x0c, 0xbf, - 0x8c, 0x45, 0x56, 0x88, 0x02, 0x46, 0x1e, 0x56, 0x9f, 0xe9, 0x86, 0x7c, 0x2b, 0x78, 0xaa, 0xab, - 0x7f, 0x17, 0x5c, 0xcc, 0xb9, 0xfc, 0x24, 0x4b, 0x30, 0xe1, 0xdd, 0x35, 0xda, 0x8b, 0x74, 0xdb, - 0xd8, 0x31, 0x65, 0x50, 0x0c, 0xe1, 0x23, 0x37, 0x51, 0x53, 0xca, 0xef, 0x27, 0x7e, 0x63, 0xac, - 0x95, 0xee, 0x03, 0x48, 0x5f, 0x4a, 0xd3, 0x6e, 0x92, 0x2d, 0x18, 0x35, 0x2c, 0xea, 0xfa, 0x51, - 0x7c, 0xbb, 0x6f, 0x2d, 0x64, 0x54, 0x90, 0x38, 0x84, 0xef, 0x7e, 0xf0, 0x0b, 0x43, 0xdc, 0xfa, - 0x3f, 0xd4, 0xe0, 0x42, 0x76, 0x18, 0x84, 0x1e, 0x44, 0x9b, 0x16, 0x8c, 0xbb, 0x51, 0x33, 0xb9, - 0xe9, 0x3f, 0xa0, 0x46, 0x12, 0x56, 0x42, 0xe7, 0x31, 0xb1, 0xaf, 0xe2, 0x3a, 0x5e, 0xb0, 0xf2, - 0xc9, 0xe0, 0xc2, 0xa1, 0x0a, 0xa7, 0xf4, 0x04, 0x55, 0xfc, 0x3c, 0xd0, 0x37, 0xa3, 0xee, 0xb5, - 0x8d, 0x3a, 0x6d, 0x9c, 0x72, 0xa2, 0xbe, 0x63, 0x88, 0xae, 0x9b, 0xdd, 0xf7, 0x93, 0x0d, 0xf4, - 0x9d, 0x43, 0xf3, 0xf0, 0x40, 0xdf, 0xd9, 0x0d, 0xdf, 0x21, 0x11, 0x68, 0xb3, 0x3b, 0x9f, 0xf3, - 0xea, 0xef, 0xb3, 0xc3, 0x79, 0xa3, 0x3d, 0x62, 0xb6, 0xbf, 0x9d, 0x13, 0xcc, 0xf6, 0x37, 0xf5, - 0xb7, 0x99, 0xfe, 0x32, 0x32, 0xfd, 0x25, 0xb2, 0xcf, 0x0d, 0x9f, 0x52, 0xf6, 0xb9, 0x37, 0x61, - 0xb8, 0x6d, 0xb8, 0xd4, 0x0e, 0xee, 0x20, 0xaa, 0xfd, 0xa6, 0xb6, 0x8c, 0xb8, 0x60, 0xf8, 0x49, - 0xae, 0x73, 0x02, 0x28, 0x09, 0x65, 0xbc, 0x1c, 0x1f, 0x3d, 0xa9, 0x97, 0xe3, 0x7f, 0xae, 0xc1, - 0x43, 0xdd, 0xd8, 0x06, 0x57, 0xf4, 0xea, 0x89, 0xcf, 0xa4, 0x1f, 0x45, 0x2f, 0xc5, 0x0d, 0x43, - 0x45, 0x2f, 0x09, 0xc1, 0x14, 0xdd, 0x9c, 0xac, 0xda, 0xa5, 0x22, 0x59, 0xb5, 0xf5, 0x5f, 0x2e, - 0x01, 0xac, 0x51, 0xff, 0xae, 0xe3, 0xde, 0x61, 0x67, 0xf0, 0x43, 0x31, 0x53, 0xd6, 0xe8, 0xd7, - 0x2f, 0xd6, 0xd3, 0x43, 0x30, 0xd8, 0x76, 0x1a, 0x9e, 0x94, 0xaf, 0x79, 0x47, 0xb8, 0x1f, 0x2b, - 0x2f, 0x25, 0x65, 0x18, 0xe2, 0x97, 0xe9, 0x52, 0xf5, 0xe1, 0x86, 0xb0, 0x35, 0x56, 0x80, 0xa2, - 0x5c, 0x24, 0x0b, 0x17, 0x26, 0x3e, 0x69, 0x29, 0x94, 0xc9, 0xc2, 0x45, 0x19, 0x86, 0x50, 0x72, - 0x15, 0xc0, 0x6c, 0x5f, 0x33, 0x5a, 0xa6, 0x65, 0xca, 0xcf, 0x69, 0x8c, 0x5b, 0x68, 0xa0, 0xba, - 0x1e, 0x94, 0xde, 0xdf, 0x2f, 0x8f, 0xca, 0x5f, 0x7b, 0xa8, 0xd4, 0xd6, 0xbf, 0xa4, 0xc1, 0x74, - 0x34, 0x79, 0x72, 0xab, 0x04, 0x3d, 0x17, 0x81, 0xf6, 0x72, 0x7b, 0x2e, 0x62, 0xab, 0x76, 0xef, - 0xb9, 0x50, 0xb4, 0xf3, 0x7a, 0xfe, 0x14, 0x8c, 0x53, 0x11, 0x8f, 0xa1, 0xba, 0x84, 0x82, 0x07, - 0x8d, 0x09, 0x75, 0x65, 0x39, 0x2a, 0x46, 0xb5, 0x8e, 0xfe, 0x57, 0x03, 0x30, 0xb1, 0xd6, 0x34, - 0xed, 0xdd, 0x20, 0xf0, 0x44, 0x78, 0x8b, 0xa3, 0x9d, 0xcc, 0x2d, 0xce, 0xab, 0x30, 0x6b, 0xa9, - 0x66, 0x57, 0x21, 0xd8, 0x18, 0x76, 0x33, 0x9c, 0x01, 0x2e, 0xa7, 0xaf, 0xe4, 0xd4, 0xc1, 0xdc, - 0xd6, 0xc4, 0x87, 0xe1, 0x7a, 0x90, 0x53, 0xa6, 0x70, 0x30, 0x05, 0x75, 0x2e, 0xe6, 0xd5, 0x77, - 0xc5, 0x21, 0x4f, 0x92, 0xdb, 0x53, 0xd2, 0x22, 0x9f, 0xd4, 0xe0, 0x3c, 0xdd, 0x15, 0xef, 0xea, - 0x37, 0x5c, 0x63, 0x6b, 0xcb, 0xac, 0xcb, 0xe7, 0x10, 0x62, 0x27, 0xae, 0x1c, 0xec, 0x97, 0xcf, - 0x2f, 0x67, 0x55, 0xb8, 0xbf, 0x5f, 0xbe, 0x92, 0x19, 0xe6, 0x80, 0xaf, 0x66, 0x66, 0x13, 0xcc, - 0x26, 0x35, 0xf7, 0x1c, 0x8c, 0x1f, 0xe1, 0x11, 0x5d, 0x2c, 0x98, 0xc1, 0xaf, 0x94, 0x60, 0x82, - 0x6d, 0xb7, 0x15, 0xa7, 0x6e, 0x58, 0x4b, 0x6b, 0x35, 0xf2, 0x44, 0x32, 0x04, 0x51, 0x68, 0xf2, - 0x4e, 0x85, 0x21, 0x5a, 0x81, 0x73, 0x5b, 0x8e, 0x5b, 0xa7, 0x1b, 0x95, 0xf5, 0x0d, 0x47, 0x3a, - 0x35, 0x2c, 0xad, 0xd5, 0xa4, 0xde, 0xc2, 0xcd, 0xaa, 0xd7, 0x32, 0xe0, 0x98, 0xd9, 0x8a, 0xdc, - 0x82, 0xf3, 0x51, 0xf9, 0xed, 0xb6, 0xf0, 0xe6, 0x64, 0xe8, 0x06, 0x22, 0x6f, 0xd4, 0x6b, 0x59, - 0x15, 0x30, 0xbb, 0x1d, 0x31, 0xe0, 0x41, 0x19, 0xff, 0xed, 0x9a, 0xe3, 0xde, 0x35, 0xdc, 0x46, - 0x1c, 0xed, 0x60, 0x74, 0xe9, 0xbb, 0x94, 0x5f, 0x0d, 0xbb, 0xe1, 0xd0, 0xdf, 0xd6, 0x20, 0x1e, - 0xe0, 0x89, 0x3c, 0x00, 0x03, 0xae, 0x4c, 0x83, 0x22, 0x03, 0x1d, 0x31, 0x11, 0x9e, 0x95, 0x91, - 0x79, 0x00, 0x37, 0x8a, 0x32, 0x55, 0x8a, 0x62, 0x0f, 0x2b, 0xf1, 0xa1, 0x94, 0x1a, 0x0c, 0x95, - 0x6f, 0x34, 0x25, 0xc3, 0xe3, 0xa8, 0x36, 0x8c, 0x26, 0xb2, 0x32, 0x1e, 0x64, 0xda, 0x6c, 0x52, - 0x2f, 0x30, 0x9b, 0x89, 0x20, 0xd3, 0xbc, 0x04, 0x25, 0x44, 0xff, 0xf1, 0x61, 0x50, 0x1e, 0xe6, - 0x1f, 0x41, 0x84, 0xfb, 0x69, 0x0d, 0xce, 0xd5, 0x2d, 0x93, 0xda, 0x7e, 0xe2, 0x8d, 0xab, 0xe0, - 0xed, 0xb7, 0x0b, 0x45, 0x0c, 0x68, 0x53, 0xbb, 0xba, 0x24, 0x1d, 0x73, 0x2b, 0x19, 0xc8, 0xa5, - 0xf3, 0x72, 0x06, 0x04, 0x33, 0x3b, 0xc3, 0xc7, 0xc3, 0xcb, 0xab, 0x4b, 0x6a, 0xd8, 0xa8, 0x8a, - 0x2c, 0xc3, 0x10, 0xca, 0xd8, 0x62, 0xd3, 0x75, 0x3a, 0x6d, 0xaf, 0xc2, 0xdf, 0xdf, 0x88, 0x19, - 0xe3, 0x6c, 0xf1, 0x7a, 0x54, 0x8c, 0x6a, 0x1d, 0xf2, 0x0c, 0x4c, 0x88, 0x9f, 0xeb, 0x2e, 0xdd, - 0x32, 0x77, 0xe5, 0x89, 0xc1, 0x6d, 0x52, 0xd7, 0x95, 0x72, 0x8c, 0xd5, 0xe2, 0x91, 0x5f, 0x3c, - 0xaf, 0x43, 0xdd, 0xdb, 0xb8, 0x22, 0x33, 0xa2, 0x89, 0xc8, 0x2f, 0x41, 0x21, 0x46, 0x70, 0xf2, - 0x63, 0x1a, 0x4c, 0xb9, 0xf4, 0xcd, 0x8e, 0xe9, 0x32, 0xf9, 0xc2, 0x30, 0x5b, 0x9e, 0x8c, 0x8e, - 0x80, 0xfd, 0x45, 0x64, 0x98, 0xc7, 0x18, 0x52, 0xc1, 0xbd, 0xc2, 0x4b, 0xbb, 0x38, 0x10, 0x13, - 0x3d, 0x60, 0x53, 0xe5, 0x99, 0x4d, 0xdb, 0xb4, 0x9b, 0x0b, 0x56, 0xd3, 0x9b, 0x1d, 0x8d, 0x4e, - 0x90, 0x5a, 0x54, 0x8c, 0x6a, 0x1d, 0xf2, 0x2c, 0x4c, 0x76, 0x3c, 0xc6, 0x93, 0x5a, 0x54, 0xcc, - 0xef, 0x58, 0x74, 0xab, 0x79, 0x5b, 0x05, 0x60, 0xbc, 0x1e, 0xb9, 0x0a, 0x53, 0x41, 0x81, 0x9c, - 0x65, 0x10, 0xf1, 0xa8, 0xb9, 0x71, 0x3e, 0x06, 0xc1, 0x44, 0xcd, 0xb9, 0x05, 0x38, 0x9b, 0x31, - 0xcc, 0x23, 0x31, 0xbe, 0xbf, 0xd6, 0xe0, 0xbc, 0x10, 0x89, 0x82, 0x5c, 0x6a, 0x41, 0xdc, 0xe5, - 0xec, 0x10, 0xc6, 0xda, 0x89, 0x86, 0x30, 0xfe, 0x3a, 0x84, 0x6a, 0xd6, 0x7f, 0xae, 0x04, 0xef, - 0x3e, 0xf4, 0xbb, 0x24, 0x3f, 0xa1, 0xc1, 0x38, 0xdd, 0xf5, 0x5d, 0x23, 0x7c, 0xa4, 0xc8, 0x36, - 0xe9, 0xd6, 0x89, 0x30, 0x81, 0xf9, 0xe5, 0x88, 0x90, 0xd8, 0xb8, 0xa1, 0x1e, 0xa2, 0x40, 0x50, - 0xed, 0x0f, 0x63, 0x85, 0x22, 0x5e, 0xbb, 0xea, 0xfe, 0x20, 0x22, 0xdc, 0xa0, 0x84, 0xcc, 0xbd, - 0x08, 0xd3, 0x49, 0xcc, 0x47, 0xda, 0x2b, 0xbf, 0x54, 0x82, 0x91, 0x75, 0xd7, 0x79, 0x83, 0xd6, - 0x4f, 0x23, 0x80, 0x94, 0x11, 0xb3, 0xb2, 0x14, 0xd2, 0x21, 0x65, 0x67, 0x73, 0xcd, 0x2a, 0x66, - 0xc2, 0xac, 0xb2, 0xd0, 0x0f, 0x91, 0xee, 0x76, 0x94, 0xdf, 0xd4, 0x60, 0x5c, 0xd6, 0x3c, 0x05, - 0xc3, 0xc9, 0x77, 0xc7, 0x0d, 0x27, 0xcf, 0xf7, 0x31, 0xae, 0x1c, 0x4b, 0xc9, 0xe7, 0x35, 0x98, - 0x94, 0x35, 0x56, 0x69, 0x6b, 0x93, 0xba, 0xe4, 0x1a, 0x8c, 0x78, 0x1d, 0xbe, 0x90, 0x72, 0x40, - 0x0f, 0xaa, 0xd6, 0x3f, 0x77, 0xd3, 0xa8, 0xb3, 0xee, 0xd7, 0x44, 0x15, 0x25, 0x2b, 0x99, 0x28, - 0xc0, 0xa0, 0x31, 0xb9, 0x0c, 0x83, 0xae, 0x63, 0xa5, 0xc2, 0x8a, 0xa2, 0x63, 0x51, 0xe4, 0x10, - 0xa6, 0x2b, 0xb0, 0xbf, 0x81, 0x1e, 0xc0, 0x75, 0x05, 0x06, 0xf6, 0x50, 0x94, 0xeb, 0x5f, 0x1a, - 0x0a, 0x27, 0x9b, 0x2b, 0x86, 0x37, 0x60, 0xac, 0xee, 0x52, 0xc3, 0xa7, 0x8d, 0xc5, 0xbd, 0x5e, - 0x3a, 0xc7, 0x8f, 0xab, 0x4a, 0xd0, 0x02, 0xa3, 0xc6, 0xec, 0x64, 0x50, 0x3d, 0x4e, 0x4a, 0xd1, - 0x21, 0x9a, 0xeb, 0x6d, 0xf2, 0xad, 0x30, 0xe4, 0xdc, 0xb5, 0x43, 0xc7, 0xd5, 0xae, 0x84, 0xf9, - 0x50, 0x6e, 0xb1, 0xda, 0x28, 0x1a, 0xa9, 0x61, 0x75, 0x07, 0xbb, 0x84, 0xd5, 0xb5, 0x60, 0xa4, - 0xc5, 0x97, 0xa1, 0xaf, 0x24, 0x55, 0xb1, 0x05, 0x55, 0xd3, 0x98, 0x72, 0xcc, 0x18, 0x90, 0x60, - 0x27, 0xbc, 0x1d, 0x58, 0x05, 0xd4, 0x13, 0x3e, 0x34, 0x15, 0x60, 0x04, 0x27, 0x7b, 0xf1, 0x78, - 0xcd, 0x23, 0xc5, 0x6d, 0x61, 0xb2, 0x7b, 0x4a, 0x88, 0x66, 0x31, 0xf5, 0x79, 0x31, 0x9b, 0xc9, - 0xcf, 0x6a, 0x70, 0xb1, 0x91, 0x9d, 0x59, 0x81, 0x1f, 0xea, 0x05, 0x5f, 0x3e, 0xe5, 0x24, 0x6b, - 0x58, 0x2c, 0xcb, 0x09, 0xcb, 0xcb, 0xe6, 0x80, 0x79, 0x9d, 0xd1, 0x7f, 0x70, 0x30, 0xfc, 0x9a, - 0xa4, 0xb6, 0x9c, 0x6d, 0xcb, 0xd0, 0x8a, 0xd8, 0x32, 0xc8, 0xb7, 0x04, 0x19, 0x14, 0x4a, 0xb1, - 0xdc, 0xc0, 0x61, 0x06, 0x85, 0x09, 0x49, 0x3a, 0x96, 0x35, 0xa1, 0x03, 0x67, 0x3d, 0xdf, 0xb0, - 0x68, 0xcd, 0x94, 0x17, 0x28, 0x9e, 0x6f, 0xb4, 0xda, 0x05, 0x52, 0x18, 0x88, 0x97, 0x90, 0x69, - 0x54, 0x98, 0x85, 0x9f, 0x7c, 0x2f, 0x8f, 0x2e, 0x63, 0x58, 0xfc, 0x82, 0x49, 0x24, 0x1b, 0x8a, - 0x88, 0x1f, 0xdd, 0xff, 0x4e, 0xc6, 0x8e, 0xc9, 0xc6, 0x87, 0xb9, 0x94, 0xc8, 0x5b, 0x70, 0x9e, - 0x89, 0x0a, 0x0b, 0x75, 0xdf, 0xdc, 0x31, 0xfd, 0xbd, 0xa8, 0x0b, 0x47, 0xcf, 0x5b, 0xc0, 0x35, - 0xb6, 0x95, 0x2c, 0x64, 0x98, 0x4d, 0x43, 0xff, 0x33, 0x0d, 0x48, 0x7a, 0xaf, 0x13, 0x0b, 0x46, - 0x1b, 0xc1, 0xd3, 0x44, 0xed, 0x58, 0xa2, 0x9e, 0x87, 0x47, 0x48, 0xf8, 0xa2, 0x31, 0xa4, 0x40, - 0x1c, 0x18, 0xbb, 0xbb, 0x6d, 0xfa, 0xd4, 0x32, 0x3d, 0xff, 0x98, 0x82, 0xac, 0x87, 0x31, 0x75, - 0x5f, 0x09, 0x10, 0x63, 0x44, 0x43, 0xff, 0xa1, 0x41, 0x18, 0x0d, 0xb3, 0xe6, 0x1c, 0xee, 0x3a, - 0xd6, 0x01, 0x52, 0x57, 0x32, 0x0f, 0xf7, 0x63, 0x77, 0xe3, 0xd2, 0x62, 0x25, 0x85, 0x0c, 0x33, - 0x08, 0x90, 0xb7, 0xe0, 0x9c, 0x69, 0x6f, 0xb9, 0x46, 0x18, 0xcf, 0xa7, 0x9f, 0x04, 0xbe, 0x5c, - 0xd9, 0xab, 0x66, 0xa0, 0xc3, 0x4c, 0x22, 0x84, 0xc2, 0x88, 0x48, 0x0e, 0x16, 0x58, 0xd6, 0xaf, - 0x16, 0x8a, 0x86, 0xc6, 0x51, 0x44, 0xec, 0x5d, 0xfc, 0xf6, 0x30, 0xc0, 0x2d, 0xa2, 0xaf, 0x89, - 0xff, 0x83, 0x4b, 0x07, 0xb9, 0xef, 0x2b, 0xc5, 0xe9, 0x45, 0xf7, 0x17, 0x22, 0xfa, 0x5a, 0xbc, - 0x10, 0x93, 0x04, 0xf5, 0x5f, 0xd7, 0x60, 0x48, 0x04, 0xd9, 0x38, 0x79, 0x51, 0xf3, 0xbb, 0x62, - 0xa2, 0x66, 0xa1, 0x1c, 0xa4, 0xbc, 0xab, 0xb9, 0xd9, 0x31, 0xbf, 0xa2, 0xc1, 0x18, 0xaf, 0x71, - 0x0a, 0xb2, 0xdf, 0xeb, 0x71, 0xd9, 0xef, 0xb9, 0xc2, 0xa3, 0xc9, 0x91, 0xfc, 0x7e, 0x7d, 0x40, - 0x8e, 0x85, 0x8b, 0x56, 0x55, 0x38, 0x2b, 0x1f, 0xed, 0xac, 0x98, 0x5b, 0x94, 0x6d, 0xf1, 0x25, - 0x63, 0x4f, 0xf8, 0x9d, 0x0c, 0xc9, 0x57, 0xdd, 0x69, 0x30, 0x66, 0xb5, 0x21, 0xbf, 0xa2, 0x31, - 0x21, 0xc6, 0x77, 0xcd, 0x7a, 0x5f, 0x17, 0x7e, 0x61, 0xdf, 0xe6, 0x57, 0x05, 0x32, 0xa1, 0x42, - 0xdd, 0x8e, 0xa4, 0x19, 0x5e, 0x7a, 0x7f, 0xbf, 0x5c, 0xce, 0xb0, 0x3b, 0x46, 0xe9, 0xe7, 0x3c, - 0xff, 0x93, 0x7f, 0xd8, 0xb5, 0x0a, 0xbf, 0xfd, 0x0e, 0x7a, 0x4c, 0x6e, 0xc0, 0x90, 0x57, 0x77, - 0xda, 0xf4, 0x28, 0x49, 0x74, 0xc3, 0x09, 0xae, 0xb1, 0x96, 0x28, 0x10, 0xcc, 0xbd, 0x01, 0x13, - 0x6a, 0xcf, 0x33, 0x54, 0xb4, 0x25, 0x55, 0x45, 0x3b, 0xb2, 0x03, 0x8d, 0xaa, 0xd2, 0xfd, 0xde, - 0x00, 0x0c, 0x23, 0x6d, 0xca, 0x94, 0x16, 0x87, 0xdc, 0xf1, 0x9b, 0x41, 0x9e, 0xaf, 0x52, 0xf1, - 0x87, 0x01, 0x6a, 0xd0, 0xf2, 0xd7, 0x1c, 0x5b, 0x99, 0x03, 0x35, 0xd5, 0x17, 0xb1, 0xc3, 0x40, - 0xff, 0x03, 0xc5, 0x13, 0x7d, 0x8a, 0x81, 0xf5, 0x12, 0xda, 0x9f, 0xfc, 0xa8, 0x06, 0xc4, 0xa8, - 0xd7, 0xa9, 0xe7, 0x21, 0xf5, 0xd8, 0xdc, 0x0b, 0x61, 0x55, 0x70, 0xd9, 0x62, 0x61, 0x1f, 0x93, - 0xd8, 0x22, 0xb1, 0x2d, 0x05, 0xf2, 0x30, 0x83, 0x78, 0x3f, 0xe9, 0x06, 0x7e, 0x4b, 0x83, 0x89, - 0x58, 0x36, 0x87, 0x56, 0x64, 0x8f, 0x2d, 0xee, 0x96, 0x11, 0xb8, 0xa3, 0x3f, 0xd8, 0xa5, 0x92, - 0xb0, 0xf1, 0xde, 0x0a, 0xe3, 0x39, 0x1f, 0x4f, 0xe2, 0x07, 0xfd, 0x73, 0x1a, 0x5c, 0x08, 0x06, - 0x14, 0x0f, 0xdc, 0x49, 0x1e, 0x87, 0x51, 0xa3, 0x6d, 0x72, 0x7b, 0xa4, 0x6a, 0xd1, 0x5d, 0x58, - 0xaf, 0xf2, 0x32, 0x0c, 0xa1, 0xb1, 0x64, 0x6a, 0xa5, 0x43, 0x93, 0xa9, 0x3d, 0xa6, 0xa4, 0x87, - 0x1b, 0x8a, 0x64, 0x97, 0x90, 0xb0, 0x70, 0x78, 0xd3, 0x3f, 0x00, 0x63, 0xb5, 0xda, 0x0d, 0xb1, - 0xa4, 0x47, 0xb8, 0x35, 0xd0, 0x3f, 0x3d, 0x00, 0x93, 0x32, 0x02, 0xb1, 0x69, 0x37, 0x4c, 0xbb, - 0x79, 0x0a, 0xe7, 0xdc, 0x06, 0x8c, 0x09, 0x53, 0xd0, 0x21, 0x29, 0xc4, 0x6b, 0x41, 0xa5, 0x64, - 0x16, 0x94, 0x10, 0x80, 0x11, 0x22, 0x72, 0x13, 0x86, 0xdf, 0x64, 0x3c, 0x37, 0xf8, 0x56, 0x7b, - 0x62, 0x7d, 0xe1, 0x87, 0xc8, 0xd9, 0xb5, 0x87, 0x12, 0x05, 0xf1, 0xf8, 0x7b, 0x09, 0x2e, 0x04, - 0xf6, 0x13, 0x0b, 0x2b, 0x36, 0xb3, 0x61, 0x72, 0xc8, 0x09, 0xf9, 0xec, 0x82, 0xff, 0xc2, 0x90, - 0x10, 0x4f, 0xe1, 0x14, 0x6b, 0xf1, 0x0e, 0x49, 0xe1, 0x14, 0xeb, 0x73, 0xce, 0x71, 0xfd, 0x1c, - 0x9c, 0xcf, 0x9c, 0x8c, 0xc3, 0x45, 0x6c, 0xfd, 0x9f, 0x96, 0x60, 0xb0, 0x46, 0x69, 0xe3, 0x14, - 0x76, 0xe6, 0xeb, 0x31, 0x09, 0xec, 0x5b, 0x0b, 0x27, 0x91, 0xca, 0xb3, 0xf4, 0x6d, 0x25, 0x2c, - 0x7d, 0x2f, 0x16, 0xa6, 0xd0, 0xdd, 0xcc, 0xf7, 0x93, 0x25, 0x00, 0x56, 0x6d, 0xd1, 0xa8, 0xdf, - 0x11, 0x1c, 0x27, 0xdc, 0xcd, 0x89, 0xf4, 0x8d, 0xe9, 0x6d, 0x78, 0x9a, 0x6e, 0x04, 0x3a, 0x0c, - 0xbb, 0xfc, 0x74, 0x94, 0x97, 0x46, 0xdc, 0x5c, 0x2c, 0xce, 0x4b, 0x94, 0x90, 0x38, 0xb7, 0x18, - 0x3c, 0x26, 0x6e, 0xa1, 0xef, 0xc2, 0x08, 0x9b, 0xa0, 0xa5, 0xb5, 0x1a, 0x69, 0x29, 0xb3, 0x53, - 0x2a, 0xae, 0x5f, 0x48, 0x74, 0x87, 0x7e, 0xe5, 0x9f, 0xd6, 0xe0, 0x4c, 0xa2, 0x6e, 0x0f, 0x7a, - 0xe6, 0x89, 0xf0, 0x4c, 0xfd, 0xd7, 0x34, 0x18, 0x65, 0x7d, 0x39, 0x05, 0x46, 0xf3, 0x9d, 0x71, - 0x46, 0xf3, 0xc1, 0xa2, 0x53, 0x9c, 0xc3, 0x5f, 0xfe, 0xa4, 0x04, 0x3c, 0x5b, 0x9b, 0xf4, 0xf7, - 0x50, 0x3c, 0x39, 0xb4, 0x1c, 0x1f, 0x94, 0xcb, 0xd2, 0x11, 0x24, 0x61, 0xe0, 0x55, 0x9c, 0x41, - 0xde, 0x1b, 0xf3, 0xf5, 0x88, 0x7d, 0x36, 0x19, 0xfe, 0x1e, 0xf7, 0x60, 0xd2, 0xdb, 0x76, 0x1c, - 0x3f, 0x8c, 0xdb, 0x34, 0x58, 0xdc, 0x98, 0xcf, 0x1f, 0x93, 0x05, 0x43, 0x11, 0xb7, 0x77, 0x35, - 0x15, 0x37, 0xc6, 0x49, 0x91, 0x79, 0x80, 0x4d, 0xcb, 0xa9, 0xdf, 0x11, 0xae, 0x26, 0xe2, 0xf1, - 0x10, 0xbf, 0xcc, 0x5e, 0x0c, 0x4b, 0x51, 0xa9, 0xd1, 0x97, 0x57, 0xcd, 0x1f, 0x69, 0x62, 0xa6, - 0x8f, 0xb0, 0x79, 0x4f, 0x91, 0xa3, 0xbc, 0x27, 0xc1, 0x51, 0x42, 0x0e, 0x99, 0xe0, 0x2a, 0xe5, - 0x40, 0x89, 0x18, 0x8c, 0x8c, 0xf7, 0xb1, 0x2c, 0xbf, 0xbf, 0x24, 0x87, 0x19, 0x26, 0xfc, 0x6b, - 0xc3, 0xa4, 0xa5, 0xe6, 0xa7, 0x95, 0xdf, 0x48, 0xa1, 0xd4, 0xb6, 0xa1, 0x1b, 0x63, 0xac, 0x18, - 0xe3, 0x04, 0xc8, 0xb3, 0x30, 0x19, 0x8c, 0x4e, 0x78, 0x13, 0x96, 0xa2, 0x97, 0x3d, 0xeb, 0x2a, - 0x00, 0xe3, 0xf5, 0xf4, 0xb7, 0x4b, 0xf0, 0xb0, 0xe8, 0x3b, 0xb7, 0x62, 0x2c, 0xd1, 0x36, 0xb5, - 0x1b, 0xd4, 0xae, 0xef, 0x71, 0x99, 0xb5, 0xe1, 0x34, 0xc9, 0x5b, 0x30, 0x7c, 0x97, 0xd2, 0x46, - 0x78, 0x1d, 0xf0, 0x4a, 0xf1, 0x7c, 0x89, 0x39, 0x24, 0x5e, 0xe1, 0xe8, 0x05, 0x47, 0x17, 0xff, - 0xa3, 0x24, 0xc9, 0x88, 0xb7, 0x5d, 0x67, 0x33, 0x14, 0xad, 0x8e, 0x9f, 0xf8, 0x3a, 0x47, 0x2f, - 0x88, 0x8b, 0xff, 0x51, 0x92, 0xd4, 0xd7, 0xe1, 0x91, 0x1e, 0x9a, 0x1e, 0x45, 0x84, 0x3e, 0x0c, - 0xa3, 0x18, 0xfd, 0x51, 0x30, 0xfe, 0xbe, 0x06, 0x8f, 0x2a, 0x28, 0x97, 0x77, 0x99, 0x54, 0x5f, - 0x31, 0xda, 0x46, 0x9d, 0xe9, 0xcd, 0x3c, 0x16, 0xcd, 0x91, 0x32, 0x94, 0x7d, 0x5a, 0x83, 0x11, - 0xe1, 0x21, 0x15, 0xb0, 0xdf, 0xd7, 0xfb, 0x9c, 0xf2, 0xdc, 0x2e, 0x05, 0xa9, 0x2f, 0x82, 0xb1, - 0x89, 0xdf, 0x1e, 0x06, 0xf4, 0xf5, 0x7f, 0x33, 0x04, 0xdf, 0xd4, 0x3b, 0x22, 0xf2, 0x47, 0x5a, - 0x32, 0x3b, 0xee, 0xf8, 0xd3, 0xad, 0x93, 0xed, 0x7c, 0x68, 0x59, 0x91, 0xca, 0xfa, 0x2b, 0xa9, - 0xe4, 0x8b, 0xc7, 0x64, 0xb4, 0x89, 0x06, 0x46, 0xfe, 0x91, 0x06, 0x13, 0xec, 0x58, 0xaa, 0x45, - 0x79, 0xb3, 0xd9, 0x48, 0xdb, 0x27, 0x3c, 0xd2, 0x35, 0x85, 0x64, 0x22, 0x68, 0x85, 0x0a, 0xc2, - 0x58, 0xdf, 0xc8, 0xed, 0xf8, 0x55, 0x9a, 0x50, 0xb7, 0x2e, 0x65, 0x49, 0x23, 0x47, 0x49, 0x6d, - 0x3a, 0x67, 0xc1, 0x54, 0x7c, 0xe6, 0x4f, 0xd2, 0xe4, 0x34, 0xf7, 0x12, 0xcc, 0xa4, 0x46, 0x7f, - 0x24, 0xe3, 0xc6, 0xdf, 0x19, 0x82, 0xb2, 0x32, 0xd5, 0x59, 0xcf, 0xd7, 0xc9, 0x17, 0x34, 0x18, - 0x37, 0x6c, 0x5b, 0xfa, 0xb2, 0x04, 0xfb, 0xb7, 0xd1, 0xe7, 0xaa, 0x66, 0x91, 0x9a, 0x5f, 0x88, - 0xc8, 0x24, 0x9c, 0x35, 0x14, 0x08, 0xaa, 0xbd, 0xe9, 0xe2, 0x2d, 0x59, 0x3a, 0x35, 0x6f, 0x49, - 0xf2, 0xb1, 0xe0, 0x20, 0x16, 0xdb, 0xe8, 0xd5, 0x13, 0x98, 0x1b, 0x7e, 0xae, 0xe7, 0x58, 0xf8, - 0x7e, 0x58, 0xe3, 0x87, 0x6c, 0x14, 0x65, 0x40, 0x9e, 0x49, 0x85, 0xfc, 0xea, 0x0e, 0x0d, 0x61, - 0x10, 0x9e, 0xdd, 0x51, 0x11, 0xc6, 0xc9, 0xcf, 0xbd, 0x08, 0xd3, 0xc9, 0xa5, 0x3c, 0xd2, 0xb6, - 0xfc, 0x57, 0x83, 0xb1, 0xb3, 0x23, 0x77, 0x3e, 0x7a, 0x30, 0xb4, 0x7e, 0x31, 0xb1, 0x7b, 0x05, - 0x4f, 0x32, 0x4f, 0x6a, 0x85, 0x8e, 0x77, 0x0b, 0x0f, 0x9c, 0xde, 0x16, 0xfe, 0xbf, 0x6e, 0x0f, - 0x2d, 0xc2, 0x79, 0x65, 0xc1, 0x94, 0x64, 0xdb, 0x4f, 0xc0, 0xc8, 0x8e, 0xe9, 0x99, 0x41, 0x1c, - 0x45, 0x45, 0x86, 0x79, 0x59, 0x14, 0x63, 0x00, 0xd7, 0x57, 0x62, 0xdc, 0x71, 0xc3, 0x69, 0x3b, - 0x96, 0xd3, 0xdc, 0x5b, 0xb8, 0x6b, 0xb8, 0x14, 0x9d, 0x8e, 0x2f, 0xb1, 0xf5, 0x2a, 0x11, 0xad, - 0xc2, 0x65, 0x05, 0x5b, 0x66, 0xb4, 0xa9, 0xa3, 0xa0, 0xfb, 0xcd, 0x91, 0x40, 0xb8, 0x97, 0xe1, - 0x33, 0x7e, 0x51, 0x83, 0x07, 0x68, 0xde, 0x61, 0x29, 0x25, 0xfd, 0x57, 0x4f, 0xea, 0x30, 0x96, - 0x91, 0xed, 0xf3, 0xc0, 0x98, 0xdf, 0x33, 0xb2, 0x17, 0x4b, 0x39, 0x5f, 0xea, 0xc7, 0x52, 0x99, - 0xb1, 0xde, 0xdd, 0x12, 0xce, 0x93, 0x9f, 0xd2, 0xe0, 0x9c, 0x95, 0xb1, 0x59, 0xe5, 0xe6, 0xaf, - 0x9d, 0x00, 0x9b, 0x10, 0x37, 0xd5, 0x59, 0x10, 0xcc, 0xec, 0x0a, 0xf9, 0x99, 0xdc, 0x30, 0x68, - 0xe2, 0x22, 0x79, 0xa3, 0xcf, 0x4e, 0x1e, 0x57, 0x44, 0xb4, 0xb7, 0x35, 0x20, 0x8d, 0x94, 0xe2, - 0x20, 0x9d, 0x94, 0x3e, 0x72, 0xec, 0xea, 0x91, 0x70, 0x35, 0x48, 0x97, 0x63, 0x46, 0x27, 0xf8, - 0x3a, 0xfb, 0x19, 0x9f, 0xaf, 0x7c, 0xee, 0xd5, 0xef, 0x3a, 0x67, 0x71, 0x06, 0xb1, 0xce, 0x59, - 0x10, 0xcc, 0xec, 0x8a, 0xfe, 0xfb, 0x23, 0xc2, 0x8e, 0xc5, 0xef, 0x82, 0x37, 0x61, 0x78, 0x93, - 0xdb, 0x3d, 0xe5, 0x77, 0x5b, 0xd8, 0xc8, 0x2a, 0xac, 0xa7, 0x42, 0x8b, 0x14, 0xff, 0xa3, 0xc4, - 0x4c, 0x5e, 0x83, 0x81, 0x86, 0x1d, 0xbc, 0xa8, 0x7c, 0xbe, 0x0f, 0x73, 0x61, 0xf4, 0xae, 0x7b, - 0x69, 0xad, 0x86, 0x0c, 0x29, 0xb1, 0x61, 0xd4, 0x96, 0xa6, 0x1f, 0xa9, 0x9d, 0x7f, 0xa8, 0x28, - 0x81, 0xd0, 0x84, 0x14, 0x1a, 0xae, 0x82, 0x12, 0x0c, 0x69, 0x30, 0x7a, 0x89, 0xbb, 0x8e, 0xc2, - 0xf4, 0x42, 0xe3, 0x67, 0x37, 0xfb, 0x32, 0x85, 0x61, 0xdf, 0x30, 0x6d, 0x3f, 0x78, 0x1d, 0xf9, - 0x42, 0x51, 0x6a, 0x1b, 0x0c, 0x4b, 0x64, 0xe1, 0xe1, 0x3f, 0x3d, 0x94, 0xc8, 0x79, 0xb6, 0x72, - 0xfe, 0x42, 0x52, 0x7e, 0x46, 0x85, 0xb7, 0x81, 0x78, 0x74, 0x29, 0xb3, 0x95, 0xf3, 0xff, 0x51, - 0x62, 0x26, 0x6f, 0xc0, 0xa8, 0x17, 0xb8, 0xa6, 0x8c, 0xf6, 0x37, 0x75, 0xa1, 0x5f, 0x8a, 0x7c, - 0x4f, 0x26, 0x1d, 0x52, 0x42, 0xfc, 0x64, 0x13, 0x46, 0x4c, 0xf1, 0x14, 0x4a, 0xc6, 0x70, 0x7c, - 0xbe, 0x8f, 0xcc, 0xc2, 0xc2, 0x50, 0x20, 0x7f, 0x60, 0x80, 0x38, 0xef, 0xfe, 0x19, 0xbe, 0x8e, - 0xf7, 0xcf, 0xfa, 0x6f, 0x82, 0xb8, 0xcb, 0x90, 0x1e, 0x89, 0x5b, 0x30, 0x1a, 0x90, 0xec, 0x27, - 0x0c, 0x41, 0x90, 0x7d, 0x5f, 0x4c, 0x77, 0x98, 0x8b, 0x3f, 0xc4, 0x4d, 0x2a, 0x59, 0xe1, 0x24, - 0xa2, 0xf4, 0x4c, 0xbd, 0x85, 0x92, 0x78, 0x93, 0x27, 0x84, 0x0e, 0x82, 0x3a, 0x0d, 0x14, 0xdf, - 0xee, 0x61, 0xc0, 0xa7, 0x58, 0x22, 0xe8, 0x20, 0x26, 0x94, 0x42, 0x24, 0xc7, 0x63, 0x73, 0xb0, - 0x90, 0xc7, 0xe6, 0x0b, 0x70, 0x46, 0x7a, 0xc8, 0x54, 0x1b, 0x94, 0x6b, 0xd0, 0xf2, 0xed, 0x0d, - 0xf7, 0x9d, 0xaa, 0xc4, 0x41, 0x98, 0xac, 0x4b, 0xfe, 0xa5, 0x06, 0xa3, 0x75, 0x29, 0xb4, 0xc8, - 0x6f, 0x7d, 0xa5, 0xbf, 0x0b, 0xaf, 0xf9, 0x40, 0x06, 0x12, 0xfa, 0xc1, 0xcb, 0x01, 0x97, 0x09, - 0x8a, 0x8f, 0xc9, 0x30, 0x13, 0xf6, 0x9a, 0xfc, 0x06, 0x53, 0x81, 0x2c, 0x9e, 0xf3, 0x9e, 0x07, - 0xce, 0x11, 0x8f, 0x82, 0x6e, 0xf5, 0x39, 0x8a, 0x85, 0x08, 0xa3, 0x18, 0xc8, 0xb7, 0x85, 0x8a, - 0x4e, 0x04, 0x39, 0xa6, 0xb1, 0xa8, 0xdd, 0x27, 0xff, 0x40, 0x83, 0x47, 0xc5, 0x4b, 0xac, 0x0a, - 0x93, 0x43, 0xb6, 0xcc, 0xba, 0xe1, 0x53, 0x11, 0xbb, 0x2a, 0x78, 0x88, 0x22, 0xfc, 0x4b, 0x47, - 0x8f, 0xec, 0x5f, 0xfa, 0xf8, 0xc1, 0x7e, 0xf9, 0xd1, 0x4a, 0x0f, 0xb8, 0xb1, 0xa7, 0x1e, 0x90, - 0x7b, 0x30, 0x69, 0xa9, 0xc1, 0x02, 0x25, 0xd3, 0x2b, 0x74, 0x9d, 0x12, 0x8b, 0x3a, 0x28, 0xf4, - 0xa7, 0x58, 0x11, 0xc6, 0x49, 0xcd, 0xdd, 0x81, 0xc9, 0xd8, 0x46, 0x3b, 0x51, 0x43, 0x94, 0x0d, - 0xd3, 0xc9, 0xfd, 0x70, 0xa2, 0xbe, 0x56, 0x37, 0x61, 0x2c, 0x3c, 0x3c, 0xc9, 0xc3, 0x0a, 0xa1, - 0x48, 0x14, 0xb9, 0x49, 0xf7, 0x04, 0xd5, 0x72, 0x4c, 0x45, 0x14, 0xb7, 0x24, 0x2f, 0xb3, 0x02, - 0x89, 0x50, 0xff, 0x6d, 0x79, 0x4b, 0xb2, 0x41, 0x5b, 0x6d, 0xcb, 0xf0, 0xe9, 0x3b, 0xff, 0x8e, - 0x5e, 0xff, 0x2f, 0x9a, 0x38, 0x6f, 0xc4, 0x51, 0x4f, 0x0c, 0x18, 0x6f, 0x89, 0xa4, 0x15, 0x3c, - 0x56, 0x94, 0x56, 0x3c, 0x4a, 0xd5, 0x6a, 0x84, 0x06, 0x55, 0x9c, 0xe4, 0x2e, 0x8c, 0x05, 0xc2, - 0x51, 0x60, 0x64, 0xb9, 0xd6, 0x9f, 0xb0, 0x12, 0xca, 0x61, 0xe1, 0xf5, 0x6f, 0x50, 0xe2, 0x61, - 0x44, 0x4b, 0x37, 0x80, 0xa4, 0xdb, 0x30, 0x3d, 0x3a, 0x78, 0xeb, 0xa1, 0xc5, 0xc3, 0x4c, 0xa7, - 0xde, 0x7b, 0x04, 0x36, 0xa4, 0x52, 0x9e, 0x0d, 0x49, 0xff, 0xd5, 0x12, 0x64, 0x66, 0x5c, 0x26, - 0x3a, 0x0c, 0x8b, 0xe7, 0x97, 0x92, 0x08, 0x17, 0xaf, 0xc4, 0xdb, 0x4c, 0x94, 0x10, 0x72, 0x4b, - 0x18, 0x77, 0xec, 0x06, 0x0f, 0xef, 0x1c, 0x71, 0x09, 0xf5, 0x11, 0xf2, 0x72, 0x56, 0x05, 0xcc, - 0x6e, 0x47, 0x76, 0x80, 0xb4, 0x8c, 0xdd, 0x24, 0xb6, 0x3e, 0x92, 0x60, 0xae, 0xa6, 0xb0, 0x61, - 0x06, 0x05, 0x76, 0x90, 0x32, 0xc9, 0xa6, 0xed, 0xd3, 0x86, 0x18, 0x62, 0x70, 0x49, 0xcb, 0x0f, - 0xd2, 0x85, 0x38, 0x08, 0x93, 0x75, 0xf5, 0xaf, 0x0d, 0xc2, 0x03, 0xf1, 0x49, 0x64, 0x5f, 0x68, - 0xf0, 0x42, 0xf2, 0xa5, 0xe0, 0x5d, 0x85, 0x98, 0xc8, 0x27, 0x92, 0xef, 0x2a, 0x66, 0x2b, 0x2e, - 0xe5, 0x47, 0xb2, 0x61, 0x79, 0x41, 0xa3, 0xd8, 0x1b, 0x8b, 0xaf, 0xc3, 0x73, 0xc7, 0x9c, 0x67, - 0x9d, 0x03, 0x27, 0xfa, 0xac, 0xf3, 0x33, 0x1a, 0xcc, 0xc5, 0x8b, 0xaf, 0x99, 0xb6, 0xe9, 0x6d, - 0xcb, 0x20, 0xc5, 0x47, 0x7f, 0xd6, 0xc1, 0xd3, 0x76, 0xad, 0xe4, 0x62, 0xc4, 0x2e, 0xd4, 0xc8, - 0x67, 0x35, 0x78, 0x30, 0x31, 0x2f, 0xb1, 0x90, 0xc9, 0x47, 0x7f, 0xe1, 0xc1, 0x1f, 0xcf, 0xaf, - 0xe4, 0xa3, 0xc4, 0x6e, 0xf4, 0xf4, 0x7f, 0x56, 0x82, 0x21, 0xee, 0x63, 0xf0, 0xce, 0x70, 0x74, - 0xe7, 0x5d, 0xcd, 0xf5, 0xb3, 0x6a, 0x26, 0xfc, 0xac, 0x5e, 0x2a, 0x4e, 0xa2, 0xbb, 0xa3, 0xd5, - 0xb7, 0xc1, 0x05, 0x5e, 0x6d, 0xa1, 0xc1, 0x0d, 0x3b, 0x1e, 0x6d, 0x2c, 0x34, 0x1a, 0x5c, 0x95, - 0x3a, 0xdc, 0xbc, 0xfe, 0x30, 0x0c, 0x74, 0x5c, 0x2b, 0x19, 0xde, 0xed, 0x36, 0xae, 0x20, 0x2b, - 0xd7, 0x3f, 0xa3, 0xc1, 0x34, 0xc7, 0xad, 0x7c, 0xbe, 0x64, 0x07, 0x46, 0x5d, 0xf9, 0x09, 0xcb, - 0xb5, 0x59, 0x29, 0x3c, 0xb4, 0x0c, 0xb6, 0x20, 0x73, 0xc2, 0xcb, 0x5f, 0x18, 0xd2, 0xd2, 0xbf, - 0x3a, 0x0c, 0xb3, 0x79, 0x8d, 0xc8, 0x8f, 0x69, 0x70, 0xa1, 0x1e, 0x49, 0x73, 0x32, 0xb3, 0xb4, - 0x6f, 0x4a, 0xe7, 0x9b, 0x82, 0xaa, 0x77, 0x65, 0x21, 0xec, 0x15, 0x0f, 0xc9, 0x5b, 0xc9, 0xa4, - 0x80, 0x39, 0x94, 0xc9, 0x5b, 0x22, 0xf4, 0x55, 0x5d, 0xf5, 0x37, 0xb9, 0x59, 0x78, 0xae, 0x94, - 0xbc, 0x03, 0x41, 0xa7, 0xc2, 0xf8, 0x57, 0xb2, 0x5c, 0x21, 0xc7, 0x88, 0x7b, 0xde, 0xf6, 0x4d, - 0xba, 0xd7, 0x36, 0xcc, 0xc0, 0xc5, 0xa2, 0x38, 0xf1, 0x5a, 0xed, 0x86, 0x44, 0x15, 0x27, 0xae, - 0x94, 0x2b, 0xe4, 0xc8, 0x27, 0x35, 0x98, 0x74, 0xd4, 0xb7, 0xf4, 0xfd, 0x78, 0xb0, 0x66, 0x3e, - 0xca, 0x17, 0x22, 0x74, 0x1c, 0x14, 0x27, 0xc9, 0xf6, 0xc4, 0x8c, 0x97, 0x3c, 0xb2, 0x24, 0x53, - 0x5b, 0x2d, 0x26, 0xdc, 0xe4, 0x9c, 0x7f, 0x42, 0x1d, 0x4f, 0x83, 0xd3, 0xe4, 0x79, 0xa7, 0xa8, - 0x5f, 0x6f, 0x44, 0xe9, 0xe5, 0x59, 0xa7, 0x86, 0x8b, 0x77, 0x6a, 0x79, 0xa3, 0xb2, 0x14, 0x43, - 0x16, 0xef, 0x54, 0x1a, 0x9c, 0x26, 0xaf, 0x7f, 0xa2, 0x04, 0x17, 0x73, 0xf6, 0xd8, 0xdf, 0x98, - 0xe0, 0x07, 0x5f, 0xd1, 0x60, 0x8c, 0xcf, 0xc1, 0x3b, 0xe4, 0x61, 0x12, 0xef, 0x6b, 0x8e, 0x27, - 0xe2, 0xaf, 0x69, 0x30, 0x93, 0x0a, 0x06, 0xdf, 0xd3, 0xb3, 0x96, 0x53, 0x73, 0x92, 0x7b, 0x2c, - 0x4a, 0x24, 0x33, 0x10, 0xbd, 0xe6, 0x4e, 0x26, 0x91, 0xd1, 0x5f, 0x81, 0xc9, 0x98, 0x23, 0xa2, - 0x12, 0x3b, 0x2b, 0x2b, 0xea, 0x97, 0x1a, 0x1a, 0xab, 0xd4, 0x2d, 0xa8, 0x57, 0xb4, 0xe5, 0xd3, - 0x9c, 0xed, 0x6f, 0xce, 0x96, 0x27, 0x72, 0xcb, 0xf3, 0x3b, 0x8b, 0xd7, 0x61, 0x98, 0x47, 0xe4, - 0x0a, 0x4e, 0xcc, 0xab, 0x85, 0x23, 0x7d, 0x79, 0x42, 0x93, 0x12, 0xff, 0xa3, 0xc4, 0xca, 0x33, - 0x84, 0x2b, 0x71, 0xea, 0xd6, 0x22, 0xa5, 0xed, 0x5c, 0x32, 0xaa, 0x1d, 0xdf, 0x92, 0xa9, 0xda, - 0x04, 0xc5, 0x8d, 0x87, 0x38, 0xcb, 0x0a, 0x85, 0x2f, 0x5f, 0x5a, 0xab, 0x89, 0xc0, 0x49, 0xe1, - 0x4d, 0xc7, 0x9b, 0x00, 0x34, 0xd8, 0xb8, 0xc1, 0x2b, 0xa7, 0x17, 0x8a, 0x05, 0x66, 0x0f, 0xb7, - 0x7f, 0x20, 0x78, 0x86, 0x45, 0x1e, 0x2a, 0x44, 0x88, 0x0b, 0xe3, 0xdb, 0xe6, 0x26, 0x75, 0x6d, - 0x21, 0x43, 0x0d, 0x15, 0x17, 0x0f, 0x6f, 0x44, 0x68, 0x84, 0x7e, 0xaf, 0x14, 0xa0, 0x4a, 0x84, - 0xb8, 0xb1, 0x28, 0x9c, 0xc3, 0xc5, 0x45, 0xa2, 0xc8, 0xe6, 0x1c, 0x8d, 0x33, 0x27, 0x02, 0xa7, - 0x0d, 0x60, 0x87, 0xa1, 0xef, 0xfa, 0xb9, 0x01, 0x89, 0x02, 0xe8, 0x09, 0xa1, 0x23, 0xfa, 0x8d, - 0x0a, 0x05, 0x36, 0xaf, 0xad, 0x28, 0xd2, 0xb1, 0xb4, 0x1f, 0xbe, 0xd4, 0x67, 0xb4, 0x69, 0x69, - 0x37, 0x89, 0x0a, 0x50, 0x25, 0xc2, 0xc6, 0xd8, 0x0a, 0xe3, 0x13, 0x4b, 0xfb, 0x60, 0xa1, 0x31, - 0x46, 0x51, 0x8e, 0x65, 0xda, 0xd8, 0xf0, 0x37, 0x2a, 0x14, 0xc8, 0x1b, 0xca, 0x45, 0x19, 0x14, - 0xb7, 0x3e, 0xf5, 0x74, 0x49, 0xf6, 0xfe, 0xc8, 0x08, 0x33, 0xce, 0xbf, 0xd3, 0x07, 0x15, 0x03, - 0x0c, 0x8f, 0xdb, 0xcc, 0x78, 0x47, 0xca, 0x20, 0x13, 0xb9, 0x3f, 0x4f, 0x74, 0x75, 0x7f, 0xae, - 0x30, 0xe9, 0x4c, 0x79, 0x8e, 0xc3, 0x19, 0xc2, 0x64, 0x74, 0xbb, 0x51, 0x4b, 0x02, 0x31, 0x5d, - 0x5f, 0x30, 0x7c, 0xda, 0xe0, 0x6d, 0xa7, 0x54, 0x86, 0x2f, 0xca, 0x30, 0x84, 0x92, 0x1d, 0x98, - 0xf0, 0x14, 0x5f, 0x6a, 0x99, 0xeb, 0xbb, 0x8f, 0xbb, 0x32, 0xe9, 0x47, 0xcd, 0x63, 0x80, 0xa9, - 0x25, 0x18, 0xa3, 0x43, 0xde, 0x52, 0x9d, 0x47, 0xa7, 0xfb, 0x8b, 0xde, 0x9b, 0x8e, 0x47, 0x1d, - 0x59, 0xd7, 0x42, 0xbf, 0x45, 0xd5, 0xa7, 0xb3, 0x13, 0x77, 0x93, 0x9c, 0x39, 0x96, 0xe0, 0x05, - 0x87, 0xba, 0x51, 0xb2, 0xa5, 0xa5, 0xbb, 0x6d, 0xc7, 0xeb, 0xb8, 0x94, 0xc7, 0xd9, 0xe7, 0xcb, - 0x43, 0xa2, 0xa5, 0x5d, 0x4e, 0x02, 0x31, 0x5d, 0x9f, 0x7c, 0xbf, 0x06, 0xd3, 0x22, 0x55, 0x3a, - 0x3b, 0xb6, 0x1c, 0x9b, 0xda, 0xbe, 0xc7, 0x73, 0x81, 0x17, 0x7c, 0x6f, 0x5b, 0x4b, 0xe0, 0x12, - 0xc7, 0x4e, 0xb2, 0x14, 0x53, 0x34, 0xd9, 0xce, 0x51, 0xc3, 0x1f, 0xf0, 0x94, 0xe2, 0x05, 0x77, - 0x8e, 0x1a, 0x5a, 0x41, 0xec, 0x1c, 0xb5, 0x04, 0x63, 0x74, 0xc8, 0xb3, 0x30, 0xe9, 0x05, 0x49, - 0x05, 0xf9, 0x0c, 0x9e, 0x8f, 0x02, 0xa9, 0xd5, 0x54, 0x00, 0xc6, 0xeb, 0x91, 0x8f, 0xc3, 0x84, - 0x7a, 0x76, 0xca, 0x44, 0xe4, 0xc7, 0x18, 0x8f, 0x57, 0xf4, 0x5c, 0x05, 0xc5, 0x08, 0x12, 0x84, - 0x0b, 0xf5, 0x48, 0x49, 0x57, 0xbf, 0xef, 0x8b, 0x7c, 0x08, 0x42, 0x99, 0xce, 0xac, 0x81, 0x39, - 0x2d, 0xc9, 0x8f, 0x67, 0xdf, 0x0b, 0xcf, 0xf2, 0x2d, 0xbd, 0x7e, 0x2c, 0xf7, 0xc2, 0xaf, 0x98, - 0xfe, 0xf6, 0xad, 0xb6, 0x08, 0xa7, 0x73, 0xd4, 0x2b, 0xe2, 0xdf, 0xd3, 0x00, 0x42, 0x6b, 0xcd, - 0x69, 0xdc, 0x41, 0x34, 0x62, 0x06, 0xac, 0xc5, 0xbe, 0xac, 0x4b, 0xb9, 0xe1, 0xd6, 0xf5, 0xdf, - 0xd5, 0x60, 0x2a, 0xaa, 0x76, 0x0a, 0xaa, 0x51, 0x3d, 0xae, 0x1a, 0xbd, 0xd8, 0xdf, 0xb8, 0x72, - 0xf4, 0xa3, 0xff, 0x5d, 0x52, 0x47, 0xc5, 0xa5, 0xdf, 0x9d, 0xd8, 0x9d, 0x3e, 0x23, 0x7d, 0xa3, - 0x9f, 0x3b, 0x7d, 0xf5, 0xc9, 0x79, 0x34, 0xde, 0x8c, 0x3b, 0xfe, 0xff, 0x37, 0x26, 0x7f, 0xf6, - 0x11, 0xec, 0x21, 0x14, 0x36, 0x03, 0xd2, 0x62, 0x02, 0x0e, 0x13, 0x46, 0xdf, 0x54, 0x8f, 0xa7, - 0x3e, 0x42, 0xa4, 0xc7, 0x06, 0xdc, 0xf5, 0x50, 0xd2, 0x7f, 0xe0, 0x0c, 0x8c, 0x2b, 0x86, 0xcd, - 0x84, 0x87, 0x82, 0x76, 0x1a, 0x1e, 0x0a, 0x3e, 0x8c, 0xd7, 0xc3, 0x5c, 0x41, 0xc1, 0xb4, 0xf7, - 0x49, 0x33, 0x3c, 0x16, 0xa3, 0x2c, 0x44, 0x1e, 0xaa, 0x64, 0x98, 0xf0, 0x16, 0xee, 0xb1, 0x81, - 0x63, 0xf0, 0x1b, 0xe9, 0xb6, 0xaf, 0x9e, 0x01, 0x08, 0xe4, 0x7f, 0xda, 0x90, 0xa1, 0x6d, 0xc3, - 0x87, 0x15, 0x55, 0xef, 0x46, 0x08, 0x43, 0xa5, 0x5e, 0xfa, 0xc6, 0x7b, 0xe8, 0xd4, 0x6e, 0xbc, - 0xd9, 0x36, 0xb0, 0x82, 0xd4, 0x97, 0x7d, 0xf9, 0x65, 0x85, 0x09, 0x34, 0xa3, 0x6d, 0x10, 0x16, - 0x79, 0xa8, 0x10, 0xc9, 0x71, 0x54, 0x19, 0x29, 0xe4, 0xa8, 0xd2, 0x81, 0xb3, 0x2e, 0xf5, 0xdd, - 0xbd, 0xca, 0x5e, 0x9d, 0xc7, 0x84, 0x77, 0x7d, 0xae, 0xc1, 0x8f, 0x16, 0x8b, 0x12, 0x86, 0x69, - 0x54, 0x98, 0x85, 0x3f, 0x26, 0x00, 0x8f, 0x75, 0x15, 0x80, 0xdf, 0x0f, 0xe3, 0x3e, 0xad, 0x6f, - 0xdb, 0x66, 0xdd, 0xb0, 0xaa, 0x4b, 0x32, 0xb6, 0x6a, 0x24, 0xcb, 0x45, 0x20, 0x54, 0xeb, 0x91, - 0x45, 0x18, 0xe8, 0x98, 0x0d, 0xa9, 0x01, 0x7c, 0x73, 0x78, 0x45, 0x50, 0x5d, 0xba, 0xbf, 0x5f, - 0x7e, 0x77, 0xe4, 0xf9, 0x11, 0x8e, 0xea, 0x4a, 0xfb, 0x4e, 0xf3, 0x8a, 0xbf, 0xd7, 0xa6, 0xde, - 0xfc, 0xed, 0xea, 0x12, 0xb2, 0xc6, 0x59, 0x4e, 0x3c, 0x13, 0x47, 0x70, 0xe2, 0x79, 0x5b, 0x83, - 0xb3, 0x46, 0xf2, 0x76, 0x83, 0x7a, 0xb3, 0x93, 0xc5, 0xb9, 0x65, 0xf6, 0x8d, 0xc9, 0xe2, 0x83, - 0x72, 0x7c, 0x67, 0x17, 0xd2, 0xe4, 0x30, 0xab, 0x0f, 0xc4, 0x05, 0xd2, 0x32, 0x9b, 0x61, 0x16, - 0x4a, 0xb9, 0xea, 0x53, 0xc5, 0xec, 0x36, 0xab, 0x29, 0x4c, 0x98, 0x81, 0x9d, 0xdc, 0x85, 0x71, - 0x45, 0x48, 0x92, 0x9a, 0xcc, 0xd2, 0x71, 0x5c, 0xc2, 0x08, 0x6d, 0x57, 0xbd, 0x60, 0x51, 0x29, - 0x85, 0xb7, 0x97, 0x8a, 0x99, 0x41, 0xde, 0xe0, 0xf1, 0x51, 0x4f, 0x17, 0xbf, 0xbd, 0xcc, 0xc6, - 0x88, 0x5d, 0xa8, 0xf1, 0xd8, 0x5c, 0x56, 0x3c, 0x59, 0xec, 0xec, 0x4c, 0xf1, 0xb7, 0xf3, 0x89, - 0xbc, 0xb3, 0x62, 0x6b, 0x26, 0x0a, 0x31, 0x49, 0x90, 0x5c, 0x03, 0x42, 0x85, 0x29, 0x3d, 0x52, - 0xce, 0xbc, 0x59, 0x12, 0x26, 0xd5, 0x25, 0xcb, 0x29, 0x28, 0x66, 0xb4, 0x20, 0x7e, 0xcc, 0x56, - 0xd2, 0x87, 0x96, 0x93, 0x4c, 0x36, 0xd0, 0xcd, 0x62, 0xa2, 0xff, 0x8e, 0x26, 0xcd, 0xab, 0xa7, - 0xe8, 0x3b, 0x73, 0xd2, 0x17, 0xaf, 0xfa, 0x2b, 0x30, 0x5b, 0x0b, 0xa2, 0xc5, 0x35, 0x12, 0xb1, - 0x8b, 0x9f, 0x87, 0x49, 0x71, 0xbd, 0xb1, 0x6a, 0xb4, 0xd7, 0x22, 0x5b, 0x78, 0xf8, 0x16, 0xba, - 0xa2, 0x02, 0x31, 0x5e, 0x57, 0xff, 0x9a, 0x06, 0x17, 0xe3, 0x98, 0x1d, 0xd7, 0xbc, 0xd7, 0x3f, - 0x62, 0xf2, 0x29, 0x0d, 0xc6, 0xa3, 0x9b, 0xbb, 0x40, 0x1c, 0x29, 0xe4, 0x73, 0x1f, 0xf4, 0x8a, - 0xba, 0xca, 0x55, 0x4e, 0x3a, 0x9b, 0x54, 0x04, 0xf4, 0x50, 0x25, 0xad, 0xff, 0xa9, 0x06, 0x29, - 0x95, 0x98, 0x6c, 0xc2, 0x08, 0x23, 0xb2, 0xb4, 0x56, 0x93, 0x7b, 0xe2, 0xf9, 0x62, 0x92, 0x12, - 0x47, 0x21, 0x0c, 0xfd, 0xf2, 0x07, 0x06, 0x88, 0x99, 0x92, 0x6d, 0x2b, 0x59, 0x07, 0xe4, 0xf6, - 0x28, 0x24, 0x8a, 0xaa, 0xd9, 0x0b, 0x84, 0xaa, 0xaa, 0x96, 0x60, 0x8c, 0x8e, 0xbe, 0x02, 0x10, - 0x99, 0x31, 0xfa, 0xf6, 0x45, 0xfb, 0x89, 0x71, 0x38, 0xdf, 0xef, 0xcb, 0x20, 0x9e, 0x4e, 0x96, - 0xee, 0x98, 0x75, 0x7f, 0x61, 0xcb, 0xa7, 0xee, 0xad, 0x5b, 0xab, 0x1b, 0xdb, 0x2e, 0xf5, 0xb6, - 0x1d, 0xab, 0x51, 0x30, 0x9f, 0x2d, 0x57, 0xb7, 0x97, 0x33, 0x31, 0x62, 0x0e, 0x25, 0x6e, 0xc2, - 0xd9, 0x11, 0xca, 0x2d, 0x32, 0x3d, 0xa2, 0xe3, 0x7a, 0xbe, 0x0c, 0x00, 0x25, 0x4c, 0x38, 0x49, - 0x20, 0xa6, 0xeb, 0x27, 0x91, 0xac, 0x98, 0x2d, 0x53, 0x24, 0x28, 0xd0, 0xd2, 0x48, 0x38, 0x10, - 0xd3, 0xf5, 0x55, 0x24, 0x62, 0xa5, 0x18, 0xa3, 0x1f, 0x4a, 0x23, 0x09, 0x81, 0x98, 0xae, 0x4f, - 0x1a, 0xf0, 0x90, 0x4b, 0xeb, 0x4e, 0xab, 0x45, 0xed, 0x86, 0xc8, 0xfc, 0x6e, 0xb8, 0x4d, 0xd3, - 0xbe, 0xe6, 0x1a, 0xbc, 0x22, 0xb7, 0x88, 0x6b, 0x3c, 0x3b, 0xdd, 0x43, 0xd8, 0xa5, 0x1e, 0x76, - 0xc5, 0x42, 0x5a, 0x70, 0x46, 0xa4, 0x85, 0x75, 0xab, 0xb6, 0x4f, 0xdd, 0x1d, 0xc3, 0x92, 0x66, - 0xef, 0xa3, 0xae, 0x18, 0x3f, 0x7c, 0x6e, 0xc7, 0x51, 0x61, 0x12, 0x37, 0xd9, 0x63, 0x22, 0xa7, - 0xec, 0x8e, 0x42, 0x72, 0xb4, 0x78, 0xc2, 0x65, 0x4c, 0xa3, 0xc3, 0x2c, 0x1a, 0xa4, 0x0a, 0x67, - 0x7d, 0xc3, 0x6d, 0x52, 0xbf, 0xb2, 0x7e, 0x7b, 0x9d, 0xba, 0x75, 0xc6, 0x63, 0x2d, 0x21, 0x81, - 0x6a, 0x02, 0xd5, 0x46, 0x1a, 0x8c, 0x59, 0x6d, 0xc8, 0xc7, 0xe1, 0xb1, 0xf8, 0xa4, 0xae, 0x38, - 0x77, 0xa9, 0xbb, 0xe8, 0x74, 0xec, 0x46, 0x1c, 0x39, 0x70, 0xe4, 0x4f, 0x1c, 0xec, 0x97, 0x1f, - 0xc3, 0x5e, 0x1a, 0x60, 0x6f, 0x78, 0xd3, 0x1d, 0xb8, 0xdd, 0x6e, 0x67, 0x76, 0x60, 0x3c, 0xaf, - 0x03, 0x39, 0x0d, 0xb0, 0x37, 0xbc, 0x04, 0xe1, 0x82, 0x98, 0x18, 0x91, 0x4b, 0x51, 0xa1, 0x38, - 0xc1, 0x29, 0xf2, 0xef, 0x77, 0x23, 0xb3, 0x06, 0xe6, 0xb4, 0x64, 0x67, 0xca, 0xe3, 0x79, 0xc3, - 0x4f, 0x91, 0x99, 0xe4, 0x64, 0xde, 0x7b, 0xb0, 0x5f, 0x7e, 0x1c, 0x7b, 0x6c, 0x83, 0x3d, 0x63, - 0xcf, 0xe8, 0x4a, 0x34, 0x11, 0xa9, 0xae, 0x4c, 0xe5, 0x75, 0x25, 0xbf, 0x0d, 0xf6, 0x8c, 0x5d, - 0x7f, 0x5b, 0x03, 0xf9, 0x7e, 0x86, 0x3c, 0x14, 0xbb, 0x0d, 0x1f, 0x4d, 0xdc, 0x84, 0x07, 0x59, - 0xae, 0x4a, 0x99, 0x59, 0xae, 0xde, 0xa3, 0x04, 0xc4, 0x1b, 0x8b, 0xe4, 0x1d, 0x81, 0x59, 0x49, - 0x01, 0xfb, 0x24, 0x8c, 0x85, 0xb2, 0x9e, 0xd4, 0xc1, 0x79, 0x74, 0xf0, 0x48, 0x28, 0x8c, 0xe0, - 0xfa, 0x6f, 0x69, 0x00, 0x51, 0x72, 0xb5, 0xde, 0x12, 0xd7, 0x1e, 0xea, 0xfc, 0xaa, 0x24, 0xdc, - 0x1d, 0xc8, 0x4d, 0xb8, 0x7b, 0x42, 0x79, 0x68, 0x7f, 0x51, 0x83, 0x33, 0xf1, 0x08, 0x85, 0x1e, - 0x79, 0x0c, 0x46, 0x64, 0x5c, 0x65, 0x19, 0x18, 0x95, 0x37, 0x95, 0x41, 0x84, 0x30, 0x80, 0xc5, - 0x2f, 0x4d, 0xfa, 0x30, 0x8a, 0x65, 0x07, 0x4a, 0x3c, 0xc4, 0x3e, 0xf5, 0xf6, 0x0c, 0x0c, 0x8b, - 0xa0, 0xbc, 0xec, 0x28, 0xce, 0x08, 0x9e, 0x70, 0xb3, 0x78, 0xec, 0xdf, 0x22, 0x0f, 0xcc, 0xd5, - 0x44, 0x3d, 0xa5, 0xae, 0x89, 0x7a, 0x50, 0xe4, 0xf7, 0xee, 0xe3, 0x82, 0xbc, 0x82, 0x55, 0x71, - 0x41, 0x1e, 0xe6, 0xf6, 0xf6, 0x63, 0x37, 0xc7, 0x83, 0xc5, 0x35, 0x13, 0x31, 0x01, 0xca, 0xfd, - 0xf1, 0x54, 0xd7, 0xbb, 0xe3, 0x20, 0xea, 0xe9, 0x50, 0x71, 0x67, 0x74, 0x39, 0xe5, 0xbd, 0x44, - 0x3d, 0x0d, 0x3e, 0xa4, 0xe1, 0xdc, 0x0f, 0x69, 0x0b, 0x46, 0xe4, 0xa7, 0x20, 0xcf, 0xf4, 0xe7, - 0xfb, 0xc8, 0xe5, 0xa8, 0x64, 0x14, 0x10, 0x05, 0x18, 0x20, 0x67, 0x82, 0x62, 0xcb, 0xd8, 0x35, - 0x5b, 0x9d, 0x16, 0x3f, 0xc8, 0x87, 0xd4, 0xaa, 0xbc, 0x18, 0x03, 0x38, 0xaf, 0x2a, 0x7c, 0xf8, - 0xf9, 0xc1, 0xab, 0x56, 0x15, 0xc5, 0x18, 0xc0, 0xc9, 0x6b, 0x30, 0xda, 0x32, 0x76, 0x6b, 0x1d, - 0xb7, 0x49, 0xe5, 0xbd, 0x71, 0xbe, 0x5e, 0xd7, 0xf1, 0x4d, 0x6b, 0xde, 0xb4, 0x7d, 0xcf, 0x77, - 0xe7, 0xab, 0xb6, 0x7f, 0xcb, 0xad, 0xf9, 0x6e, 0x98, 0x2d, 0x77, 0x55, 0x62, 0xc1, 0x10, 0x1f, - 0xb1, 0x60, 0xaa, 0x65, 0xec, 0xde, 0xb6, 0x0d, 0x11, 0xd0, 0x56, 0x1e, 0x94, 0x45, 0x28, 0x70, - 0xc7, 0xa1, 0xd5, 0x18, 0x2e, 0x4c, 0xe0, 0xce, 0xf0, 0x51, 0x9a, 0x38, 0x29, 0x1f, 0xa5, 0x85, - 0xf0, 0x95, 0xa8, 0xb0, 0x34, 0x3d, 0x90, 0x19, 0x5f, 0xa6, 0xeb, 0x0b, 0xd0, 0xd7, 0xc3, 0x17, - 0xa0, 0x53, 0xc5, 0x9d, 0x6a, 0xba, 0xbc, 0xfe, 0xec, 0xc0, 0x38, 0xd3, 0xaa, 0x45, 0xa9, 0x37, - 0x7b, 0xa6, 0xf8, 0xa5, 0xc9, 0x52, 0x88, 0x26, 0x62, 0x49, 0x51, 0x99, 0x87, 0x2a, 0x1d, 0x72, - 0x0b, 0xce, 0xcb, 0xcc, 0xfb, 0x51, 0x15, 0xae, 0xf6, 0x4e, 0xf3, 0xef, 0x87, 0xbf, 0x8a, 0xb8, - 0x99, 0x55, 0x01, 0xb3, 0xdb, 0x45, 0xb1, 0xd0, 0x66, 0xb2, 0x63, 0xa1, 0x91, 0x1f, 0xca, 0xba, - 0x0d, 0x26, 0x7c, 0x4e, 0x3f, 0x5c, 0x9c, 0x37, 0x14, 0xbe, 0x13, 0xfe, 0xe7, 0x1a, 0xcc, 0xca, - 0x5d, 0x26, 0x6f, 0x70, 0x2d, 0xea, 0xae, 0x1a, 0xb6, 0xd1, 0xa4, 0xae, 0x34, 0xdf, 0x6c, 0xf4, - 0xc1, 0x1f, 0x52, 0x38, 0xc3, 0xa7, 0xb9, 0x8f, 0x1e, 0xec, 0x97, 0x2f, 0x1f, 0x56, 0x0b, 0x73, - 0xfb, 0x46, 0x5c, 0x18, 0xf1, 0xf6, 0xbc, 0xba, 0x6f, 0x79, 0xb3, 0xe7, 0xf8, 0x66, 0xb9, 0xde, - 0x07, 0x67, 0xad, 0x09, 0x4c, 0x82, 0xb5, 0x46, 0x79, 0x6c, 0x44, 0x29, 0x06, 0x84, 0xc8, 0x8f, - 0x6a, 0x30, 0x23, 0x6d, 0xba, 0x4a, 0xf8, 0x83, 0xf3, 0xc5, 0x7d, 0xc7, 0x2b, 0x49, 0x64, 0xc1, - 0xad, 0x2d, 0x57, 0x08, 0x53, 0x50, 0x4c, 0x53, 0xef, 0x37, 0x3e, 0x49, 0x1f, 0x21, 0xa9, 0xe7, - 0xae, 0xc2, 0x84, 0x3a, 0x71, 0x47, 0x0a, 0x8b, 0xf2, 0xd3, 0x1a, 0x4c, 0x27, 0x0f, 0x52, 0xb2, - 0x0d, 0x23, 0xf2, 0xab, 0x92, 0xf6, 0x99, 0x85, 0xa2, 0x9e, 0x5d, 0x16, 0x95, 0x6f, 0xa3, 0x84, - 0x5c, 0x26, 0x8b, 0x30, 0x40, 0xaf, 0x7a, 0x6d, 0x96, 0xba, 0x78, 0x6d, 0xbe, 0x00, 0x17, 0xb2, - 0xbf, 0x2f, 0x26, 0xd5, 0x1a, 0x96, 0xe5, 0xdc, 0x95, 0x46, 0x90, 0x28, 0x25, 0x28, 0x2b, 0x44, - 0x01, 0xd3, 0x3f, 0x06, 0xc9, 0xa4, 0x08, 0xe4, 0x0d, 0x18, 0xf3, 0xbc, 0x6d, 0x71, 0x17, 0x2f, - 0x07, 0x59, 0xcc, 0x74, 0x18, 0x04, 0xa8, 0x16, 0x82, 0x78, 0xf8, 0x13, 0x23, 0xf4, 0x8b, 0xaf, - 0x7e, 0xf9, 0x6b, 0x97, 0xde, 0xf5, 0xdb, 0x5f, 0xbb, 0xf4, 0xae, 0xaf, 0x7e, 0xed, 0xd2, 0xbb, - 0xbe, 0xe7, 0xe0, 0x92, 0xf6, 0xe5, 0x83, 0x4b, 0xda, 0x6f, 0x1f, 0x5c, 0xd2, 0xbe, 0x7a, 0x70, - 0x49, 0xfb, 0x8f, 0x07, 0x97, 0xb4, 0x1f, 0xf9, 0x4f, 0x97, 0xde, 0xf5, 0xda, 0xd3, 0x11, 0xf5, - 0x2b, 0x01, 0xd1, 0xe8, 0x9f, 0xf6, 0x9d, 0xe6, 0x15, 0x46, 0x3d, 0x78, 0x10, 0xcb, 0xa9, 0xff, - 0x9f, 0x00, 0x00, 0x00, 0xff, 0xff, 0x13, 0x35, 0x1b, 0x68, 0xf9, 0x06, 0x01, 0x00, + // 13423 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xec, 0x7d, 0x6d, 0x70, 0x25, 0xd9, + 0x55, 0x98, 0xfb, 0xe9, 0xfb, 0xe8, 0x63, 0xa4, 0x3b, 0x5f, 0x5a, 0xed, 0xec, 0xbc, 0x71, 0xef, + 0xae, 0xb3, 0xcb, 0xda, 0x1a, 0x76, 0x58, 0x7b, 0xbd, 0xb3, 0xec, 0xae, 0xa5, 0xf7, 0x34, 0x33, + 0xcf, 0x23, 0x69, 0xe4, 0xfb, 0x34, 0x3b, 0xcb, 0x02, 0x0b, 0xad, 0xd7, 0x57, 0x4f, 0xbd, 0xd3, + 0xaf, 0xfb, 0x6d, 0x77, 0x3f, 0x8d, 0x34, 0x6b, 0xc7, 0xd8, 0xe1, 0xc3, 0x36, 0x98, 0x02, 0x92, + 0xe0, 0x5a, 0x1b, 0x0a, 0x13, 0x0a, 0x48, 0x42, 0xca, 0x49, 0x91, 0x22, 0x29, 0xa0, 0x52, 0x95, + 0xb8, 0x2a, 0xc1, 0xa6, 0x80, 0x50, 0x40, 0x2a, 0xa6, 0x12, 0x44, 0xac, 0x10, 0x48, 0x55, 0x52, + 0x24, 0x15, 0x2a, 0xa1, 0x98, 0x50, 0x90, 0xba, 0x5f, 0xdd, 0xb7, 0xbf, 0x9e, 0x9e, 0xfa, 0x49, + 0xb2, 0x37, 0xf0, 0x4b, 0x7a, 0xf7, 0xdc, 0x7b, 0xce, 0xfd, 0xea, 0x73, 0xcf, 0x39, 0xf7, 0xdc, + 0x73, 0x60, 0xb1, 0x69, 0x05, 0x5b, 0x9d, 0x8d, 0xf9, 0x86, 0xdb, 0xba, 0xdc, 0x34, 0x3c, 0x93, + 0x38, 0xc4, 0x8b, 0xfe, 0x69, 0xdf, 0x6d, 0x5e, 0x36, 0xda, 0x96, 0x7f, 0xb9, 0xe1, 0x7a, 0xe4, + 0xf2, 0xf6, 0xd3, 0x1b, 0x24, 0x30, 0x9e, 0xbe, 0xdc, 0xa4, 0x30, 0x23, 0x20, 0xe6, 0x7c, 0xdb, + 0x73, 0x03, 0x17, 0x5d, 0x89, 0x70, 0xcc, 0xcb, 0xa6, 0xd1, 0x3f, 0xed, 0xbb, 0xcd, 0x79, 0x8a, + 0x63, 0x9e, 0xe2, 0x98, 0x17, 0x38, 0xe6, 0xde, 0xa3, 0xd2, 0x75, 0x9b, 0xee, 0x65, 0x86, 0x6a, + 0xa3, 0xb3, 0xc9, 0x7e, 0xb1, 0x1f, 0xec, 0x3f, 0x4e, 0x62, 0xee, 0xc9, 0xbb, 0xef, 0xf7, 0xe7, + 0x2d, 0x97, 0x76, 0xe6, 0xb2, 0xd1, 0x09, 0x5c, 0xbf, 0x61, 0xd8, 0x96, 0xd3, 0xbc, 0xbc, 0x9d, + 0xea, 0xcd, 0x9c, 0xae, 0x54, 0x15, 0xdd, 0xee, 0x5a, 0xc7, 0xdb, 0x30, 0x1a, 0x59, 0x75, 0x6e, + 0x44, 0x75, 0xc8, 0x4e, 0x40, 0x1c, 0xdf, 0x72, 0x1d, 0xff, 0x3d, 0x74, 0x24, 0xc4, 0xdb, 0x56, + 0xe7, 0x26, 0x56, 0x21, 0x0b, 0xd3, 0x33, 0x11, 0xa6, 0x96, 0xd1, 0xd8, 0xb2, 0x1c, 0xe2, 0xed, + 0xca, 0xe6, 0x97, 0x3d, 0xe2, 0xbb, 0x1d, 0xaf, 0x41, 0x0e, 0xd5, 0xca, 0xbf, 0xdc, 0x22, 0x81, + 0x91, 0x45, 0xeb, 0x72, 0x5e, 0x2b, 0xaf, 0xe3, 0x04, 0x56, 0x2b, 0x4d, 0xe6, 0x7d, 0x07, 0x35, + 0xf0, 0x1b, 0x5b, 0xa4, 0x65, 0xa4, 0xda, 0x7d, 0x53, 0x5e, 0xbb, 0x4e, 0x60, 0xd9, 0x97, 0x2d, + 0x27, 0xf0, 0x03, 0x2f, 0xd9, 0x48, 0xff, 0x94, 0x06, 0xd3, 0x0b, 0x6b, 0xb5, 0x3a, 0x9b, 0xc1, + 0x65, 0xb7, 0xd9, 0xb4, 0x9c, 0x26, 0x7a, 0x0a, 0xc6, 0xb6, 0x89, 0xb7, 0xe1, 0xfa, 0x56, 0xb0, + 0x3b, 0xab, 0x5d, 0xd2, 0x9e, 0x18, 0x5a, 0x9c, 0xdc, 0xdf, 0x2b, 0x8f, 0xbd, 0x2c, 0x0b, 0x71, + 0x04, 0x47, 0x35, 0x38, 0xbd, 0x15, 0x04, 0xed, 0x85, 0x46, 0x83, 0xf8, 0x7e, 0x58, 0x63, 0xb6, + 0xc4, 0x9a, 0x9d, 0xdf, 0xdf, 0x2b, 0x9f, 0xbe, 0xb1, 0xbe, 0xbe, 0x96, 0x00, 0xe3, 0xac, 0x36, + 0xfa, 0xcf, 0x6b, 0x30, 0x13, 0x76, 0x06, 0x93, 0x37, 0x3a, 0xc4, 0x0f, 0x7c, 0x84, 0xe1, 0x5c, + 0xcb, 0xd8, 0x59, 0x75, 0x9d, 0x95, 0x4e, 0x60, 0x04, 0x96, 0xd3, 0xac, 0x39, 0x9b, 0xb6, 0xd5, + 0xdc, 0x0a, 0x44, 0xd7, 0xe6, 0xf6, 0xf7, 0xca, 0xe7, 0x56, 0x32, 0x6b, 0xe0, 0x9c, 0x96, 0xb4, + 0xd3, 0x2d, 0x63, 0x27, 0x85, 0x50, 0xe9, 0xf4, 0x4a, 0x1a, 0x8c, 0xb3, 0xda, 0xe8, 0xef, 0x85, + 0x19, 0x3e, 0x0e, 0x4c, 0xfc, 0xc0, 0xb3, 0x1a, 0x81, 0xe5, 0x3a, 0xe8, 0x12, 0x0c, 0x3a, 0x46, + 0x8b, 0xb0, 0x1e, 0x8e, 0x2d, 0x4e, 0x7c, 0x69, 0xaf, 0xfc, 0x8e, 0xfd, 0xbd, 0xf2, 0xe0, 0xaa, + 0xd1, 0x22, 0x98, 0x41, 0xf4, 0xff, 0x53, 0x82, 0x0b, 0xa9, 0x76, 0x77, 0xac, 0x60, 0xeb, 0x56, + 0x9b, 0xfe, 0xe7, 0xa3, 0x1f, 0xd4, 0x60, 0xc6, 0x48, 0x56, 0x60, 0x08, 0xc7, 0xaf, 0x2c, 0xcd, + 0x1f, 0xfe, 0x03, 0x9f, 0x4f, 0x51, 0x5b, 0x7c, 0x48, 0xf4, 0x2b, 0x3d, 0x00, 0x9c, 0x26, 0x8d, + 0x3e, 0xa1, 0xc1, 0x88, 0xcb, 0x3b, 0x37, 0x5b, 0xba, 0x34, 0xf0, 0xc4, 0xf8, 0x95, 0x6f, 0x3f, + 0x92, 0x6e, 0x28, 0x83, 0x9e, 0x17, 0x7f, 0x97, 0x9c, 0xc0, 0xdb, 0x5d, 0x3c, 0x25, 0xba, 0x37, + 0x22, 0x4a, 0xb1, 0x24, 0x3f, 0x77, 0x15, 0x26, 0xd4, 0x9a, 0x68, 0x1a, 0x06, 0xee, 0x12, 0xbe, + 0x55, 0xc7, 0x30, 0xfd, 0x17, 0x9d, 0x81, 0xa1, 0x6d, 0xc3, 0xee, 0x10, 0xb6, 0xa4, 0x63, 0x98, + 0xff, 0xb8, 0x5a, 0x7a, 0xbf, 0xa6, 0x5f, 0x81, 0xa1, 0x05, 0xd3, 0x74, 0x1d, 0xf4, 0x24, 0x8c, + 0x10, 0xc7, 0xd8, 0xb0, 0x89, 0xc9, 0x1a, 0x8e, 0x46, 0xf4, 0x96, 0x78, 0x31, 0x96, 0x70, 0xfd, + 0xef, 0x96, 0x60, 0x98, 0x35, 0xf2, 0xd1, 0x8f, 0x68, 0x70, 0xfa, 0x6e, 0x67, 0x83, 0x78, 0x0e, + 0x09, 0x88, 0x5f, 0x35, 0xfc, 0xad, 0x0d, 0xd7, 0xf0, 0x4c, 0xb1, 0x30, 0xd7, 0x8b, 0xcc, 0xc8, + 0xcd, 0x34, 0x3a, 0xbe, 0x07, 0x33, 0x00, 0x38, 0x8b, 0x38, 0xda, 0x86, 0x09, 0xa7, 0x69, 0x39, + 0x3b, 0x35, 0xa7, 0xe9, 0x11, 0xdf, 0x67, 0x83, 0x1e, 0xbf, 0xf2, 0x81, 0x22, 0x9d, 0x59, 0x55, + 0xf0, 0x2c, 0x4e, 0xef, 0xef, 0x95, 0x27, 0xd4, 0x12, 0x1c, 0xa3, 0xa3, 0xff, 0x85, 0x06, 0xa7, + 0x16, 0xcc, 0x96, 0xe5, 0x53, 0x4e, 0xbb, 0x66, 0x77, 0x9a, 0x56, 0x0f, 0x5b, 0x1f, 0x7d, 0x08, + 0x86, 0x1b, 0xae, 0xb3, 0x69, 0x35, 0x45, 0x3f, 0xdf, 0x33, 0xcf, 0x39, 0xd7, 0xbc, 0xca, 0xb9, + 0x58, 0xf7, 0x04, 0xc7, 0x9b, 0xc7, 0xc6, 0xbd, 0x25, 0xc9, 0xd0, 0x17, 0x61, 0x7f, 0xaf, 0x3c, + 0x5c, 0x61, 0x08, 0xb0, 0x40, 0x84, 0x9e, 0x80, 0x51, 0xd3, 0xf2, 0xf9, 0x62, 0x0e, 0xb0, 0xc5, + 0x9c, 0xd8, 0xdf, 0x2b, 0x8f, 0x56, 0x45, 0x19, 0x0e, 0xa1, 0x68, 0x19, 0xce, 0xd0, 0x19, 0xe4, + 0xed, 0xea, 0xa4, 0xe1, 0x91, 0x80, 0x76, 0x6d, 0x76, 0x90, 0x75, 0x77, 0x76, 0x7f, 0xaf, 0x7c, + 0xe6, 0x66, 0x06, 0x1c, 0x67, 0xb6, 0xd2, 0xaf, 0xc1, 0xe8, 0x82, 0x4d, 0x3c, 0xca, 0x10, 0xd0, + 0x55, 0x98, 0x22, 0x2d, 0xc3, 0xb2, 0x31, 0x69, 0x10, 0x6b, 0x9b, 0x78, 0xfe, 0xac, 0x76, 0x69, + 0xe0, 0x89, 0xb1, 0x45, 0xb4, 0xbf, 0x57, 0x9e, 0x5a, 0x8a, 0x41, 0x70, 0xa2, 0xa6, 0xfe, 0x31, + 0x0d, 0xc6, 0x17, 0x3a, 0xa6, 0x15, 0xf0, 0x71, 0x21, 0x0f, 0xc6, 0x0d, 0xfa, 0x73, 0xcd, 0xb5, + 0xad, 0xc6, 0xae, 0xd8, 0x5c, 0x2f, 0x15, 0xfa, 0xdc, 0x22, 0x34, 0x8b, 0xa7, 0xf6, 0xf7, 0xca, + 0xe3, 0x4a, 0x01, 0x56, 0x89, 0xe8, 0x5b, 0xa0, 0xc2, 0xd0, 0xb7, 0xc0, 0x04, 0x1f, 0xee, 0x8a, + 0xd1, 0xc6, 0x64, 0x53, 0xf4, 0xe1, 0x51, 0x65, 0xad, 0x24, 0xa1, 0xf9, 0x5b, 0x1b, 0xaf, 0x93, + 0x46, 0x80, 0xc9, 0x26, 0xf1, 0x88, 0xd3, 0x20, 0x7c, 0xdb, 0x54, 0x94, 0xc6, 0x38, 0x86, 0x4a, + 0xff, 0xdb, 0x1a, 0x3c, 0xb2, 0xd0, 0x09, 0xb6, 0x5c, 0xcf, 0xba, 0x4f, 0xbc, 0x68, 0xba, 0x43, + 0x0c, 0xe8, 0x45, 0x98, 0x32, 0xc2, 0x0a, 0xab, 0xd1, 0x76, 0x3a, 0x27, 0xb6, 0xd3, 0xd4, 0x42, + 0x0c, 0x8a, 0x13, 0xb5, 0xd1, 0x15, 0x00, 0x3f, 0x5a, 0x5b, 0xc6, 0x03, 0x16, 0x91, 0x68, 0x0b, + 0xca, 0xaa, 0x2a, 0xb5, 0xf4, 0xdf, 0xa7, 0x47, 0xe1, 0xb6, 0x61, 0xd9, 0xc6, 0x86, 0x65, 0x5b, + 0xc1, 0xee, 0xab, 0xae, 0x43, 0x7a, 0xd8, 0xcd, 0xb7, 0xe1, 0x7c, 0xc7, 0x31, 0x78, 0x3b, 0x9b, + 0xac, 0xf0, 0xfd, 0xbb, 0xbe, 0xdb, 0x26, 0x9c, 0x4b, 0x8e, 0x2d, 0x3e, 0xbc, 0xbf, 0x57, 0x3e, + 0x7f, 0x3b, 0xbb, 0x0a, 0xce, 0x6b, 0x4b, 0x4f, 0x3d, 0x05, 0xf4, 0xb2, 0x6b, 0x77, 0x5a, 0x02, + 0xeb, 0x00, 0xc3, 0xca, 0x4e, 0xbd, 0xdb, 0x99, 0x35, 0x70, 0x4e, 0x4b, 0xfd, 0x4b, 0x25, 0x98, + 0x58, 0x34, 0x1a, 0x77, 0x3b, 0xed, 0xc5, 0x4e, 0xe3, 0x2e, 0x09, 0xd0, 0x77, 0xc2, 0x28, 0x15, + 0x5b, 0x4c, 0x23, 0x30, 0xc4, 0xfa, 0x7e, 0x63, 0xee, 0xb7, 0xc8, 0xb6, 0x16, 0xad, 0x1d, 0xad, + 0xf8, 0x0a, 0x09, 0x8c, 0x68, 0x5a, 0xa3, 0x32, 0x1c, 0x62, 0x45, 0x9b, 0x30, 0xe8, 0xb7, 0x49, + 0x43, 0x7c, 0xe9, 0xd5, 0x22, 0x3b, 0x58, 0xed, 0x71, 0xbd, 0x4d, 0x1a, 0xd1, 0x2a, 0xd0, 0x5f, + 0x98, 0xe1, 0x47, 0x0e, 0x0c, 0xfb, 0x81, 0x11, 0x74, 0x7c, 0xf6, 0xf9, 0x8f, 0x5f, 0xb9, 0xd6, + 0x37, 0x25, 0x86, 0x6d, 0x71, 0x4a, 0xd0, 0x1a, 0xe6, 0xbf, 0xb1, 0xa0, 0xa2, 0xff, 0x7b, 0x0d, + 0xa6, 0xd5, 0xea, 0xcb, 0x96, 0x1f, 0xa0, 0x6f, 0x4b, 0x4d, 0xe7, 0x7c, 0x6f, 0xd3, 0x49, 0x5b, + 0xb3, 0xc9, 0x9c, 0x16, 0xe4, 0x46, 0x65, 0x89, 0x32, 0x95, 0x04, 0x86, 0xac, 0x80, 0xb4, 0xe4, + 0xe1, 0xfb, 0x81, 0x7e, 0x47, 0xb8, 0x38, 0x29, 0x88, 0x0d, 0xd5, 0x28, 0x5a, 0xcc, 0xb1, 0xeb, + 0xdf, 0x09, 0x67, 0xd4, 0x5a, 0x6b, 0x9e, 0xbb, 0x6d, 0x99, 0xc4, 0xa3, 0x5f, 0x42, 0xb0, 0xdb, + 0x4e, 0x7d, 0x09, 0x74, 0x67, 0x61, 0x06, 0x41, 0xef, 0x82, 0x61, 0x8f, 0x34, 0xa9, 0x94, 0xc2, + 0x3f, 0xb8, 0x70, 0xee, 0x30, 0x2b, 0xc5, 0x02, 0xaa, 0xff, 0xef, 0x52, 0x7c, 0xee, 0xe8, 0x32, + 0xa2, 0x6d, 0x18, 0x6d, 0x0b, 0x52, 0x62, 0xee, 0x6e, 0xf4, 0x3b, 0x40, 0xd9, 0xf5, 0x68, 0x56, + 0x65, 0x09, 0x0e, 0x69, 0x21, 0x0b, 0xa6, 0xe4, 0xff, 0x95, 0x3e, 0x0e, 0x25, 0xc6, 0xe4, 0xd7, + 0x62, 0x88, 0x70, 0x02, 0x31, 0x5a, 0x87, 0x31, 0xce, 0x6e, 0x28, 0x3b, 0x1d, 0xc8, 0x67, 0xa7, + 0x75, 0x59, 0x49, 0xb0, 0xd3, 0x19, 0xd1, 0xfd, 0xb1, 0x10, 0x80, 0x23, 0x44, 0xf4, 0xe8, 0xf3, + 0x09, 0x31, 0x95, 0x43, 0x8c, 0x1d, 0x7d, 0x75, 0x51, 0x86, 0x43, 0xa8, 0xfe, 0xf9, 0x41, 0x40, + 0xe9, 0x2d, 0xae, 0xce, 0x00, 0x2f, 0x11, 0xf3, 0xdf, 0xcf, 0x0c, 0x88, 0xaf, 0x25, 0x81, 0x18, + 0xdd, 0x87, 0x49, 0xdb, 0xf0, 0x83, 0x5b, 0x6d, 0xaa, 0x83, 0xc8, 0x8d, 0x32, 0x7e, 0x65, 0xa1, + 0xc8, 0x4a, 0x2f, 0xab, 0x88, 0x16, 0x67, 0xf6, 0xf7, 0xca, 0x93, 0xb1, 0x22, 0x1c, 0x27, 0x85, + 0x5e, 0x87, 0x31, 0x5a, 0xb0, 0xe4, 0x79, 0xae, 0x27, 0x66, 0xff, 0x85, 0xa2, 0x74, 0x19, 0x12, + 0xae, 0x13, 0x85, 0x3f, 0x71, 0x84, 0x1e, 0x7d, 0x10, 0x90, 0xbb, 0xc1, 0xb4, 0x52, 0xf3, 0x3a, + 0x57, 0xb8, 0xe8, 0x60, 0xe9, 0xea, 0x0c, 0x2c, 0xce, 0x89, 0xd5, 0x44, 0xb7, 0x52, 0x35, 0x70, + 0x46, 0x2b, 0x74, 0x17, 0x50, 0xa8, 0xb4, 0x85, 0x1b, 0x60, 0x76, 0xa8, 0xf7, 0xed, 0x73, 0x8e, + 0x12, 0xbb, 0x9e, 0x42, 0x81, 0x33, 0xd0, 0xea, 0xff, 0xba, 0x04, 0xe3, 0x7c, 0x8b, 0x70, 0xc1, + 0xfa, 0xf8, 0x0f, 0x08, 0x12, 0x3b, 0x20, 0x2a, 0xc5, 0xbf, 0x79, 0xd6, 0xe1, 0xdc, 0xf3, 0xa1, + 0x95, 0x38, 0x1f, 0x96, 0xfa, 0x25, 0xd4, 0xfd, 0x78, 0xf8, 0x77, 0x1a, 0x9c, 0x52, 0x6a, 0x9f, + 0xc0, 0xe9, 0x60, 0xc6, 0x4f, 0x87, 0x97, 0xfa, 0x1c, 0x5f, 0xce, 0xe1, 0xe0, 0xc6, 0x86, 0xc5, + 0x18, 0xf7, 0x15, 0x80, 0x0d, 0xc6, 0x4e, 0x14, 0x31, 0x2d, 0x5c, 0xf2, 0xc5, 0x10, 0x82, 0x95, + 0x5a, 0x31, 0x9e, 0x55, 0xea, 0xca, 0xb3, 0xfe, 0xcb, 0x00, 0xcc, 0xa4, 0xa6, 0x3d, 0xcd, 0x47, + 0xb4, 0xaf, 0x11, 0x1f, 0x29, 0x7d, 0x2d, 0xf8, 0xc8, 0x40, 0x21, 0x3e, 0xd2, 0xf3, 0x39, 0x81, + 0x3c, 0x40, 0x2d, 0xab, 0xc9, 0x9b, 0xd5, 0x03, 0xc3, 0x0b, 0xd6, 0xad, 0x16, 0x11, 0x1c, 0xe7, + 0x1b, 0x7a, 0xdb, 0xb2, 0xb4, 0x05, 0x67, 0x3c, 0x2b, 0x29, 0x4c, 0x38, 0x03, 0xbb, 0xfe, 0xb7, + 0x4a, 0x30, 0xb2, 0x68, 0xf8, 0xac, 0xa7, 0x1f, 0x81, 0x09, 0x81, 0xba, 0xd6, 0x32, 0x9a, 0xa4, + 0x1f, 0xd5, 0x5a, 0xa0, 0x5c, 0x51, 0xd0, 0x71, 0xed, 0x44, 0x2d, 0xc1, 0x31, 0x72, 0x68, 0x17, + 0xc6, 0x5b, 0x91, 0x24, 0x2e, 0x96, 0xf8, 0x5a, 0xff, 0xd4, 0x29, 0x36, 0xae, 0x82, 0x29, 0x05, + 0x58, 0xa5, 0xa5, 0xbf, 0x06, 0xa7, 0x33, 0x7a, 0xdc, 0x83, 0x12, 0xf2, 0x38, 0x8c, 0x50, 0x3d, + 0x32, 0x92, 0xbd, 0xc6, 0xf7, 0xf7, 0xca, 0x23, 0x2f, 0xf3, 0x22, 0x2c, 0x61, 0xfa, 0xfb, 0xa8, + 0x00, 0x90, 0xec, 0x53, 0x0f, 0xc6, 0xaa, 0xdf, 0x1a, 0x04, 0xa8, 0x2c, 0x60, 0x37, 0xe0, 0x5b, + 0xe9, 0x25, 0x18, 0x6a, 0x6f, 0x19, 0xbe, 0x6c, 0xf1, 0xa4, 0x64, 0x15, 0x6b, 0xb4, 0xf0, 0xc1, + 0x5e, 0x79, 0xb6, 0xe2, 0x11, 0x93, 0x38, 0x81, 0x65, 0xd8, 0xbe, 0x6c, 0xc4, 0x60, 0x98, 0xb7, + 0xa3, 0x3b, 0x8c, 0x6e, 0xf2, 0x8a, 0xdb, 0x6a, 0xdb, 0x84, 0x42, 0xd9, 0x0e, 0x2b, 0x15, 0xdb, + 0x61, 0xcb, 0x29, 0x4c, 0x38, 0x03, 0xbb, 0xa4, 0x59, 0x73, 0xac, 0xc0, 0x32, 0x42, 0x9a, 0x03, + 0xc5, 0x69, 0xc6, 0x31, 0xe1, 0x0c, 0xec, 0xe8, 0x53, 0x1a, 0xcc, 0xc5, 0x8b, 0xaf, 0x59, 0x8e, + 0xe5, 0x6f, 0x11, 0x93, 0x11, 0x1f, 0x3c, 0x34, 0xf1, 0x8b, 0xfb, 0x7b, 0xe5, 0xb9, 0xe5, 0x5c, + 0x8c, 0xb8, 0x0b, 0x35, 0xf4, 0x69, 0x0d, 0x1e, 0x4e, 0xcc, 0x8b, 0x67, 0x35, 0x9b, 0xc4, 0x13, + 0xbd, 0x39, 0xfc, 0x07, 0x5e, 0xde, 0xdf, 0x2b, 0x3f, 0xbc, 0x9c, 0x8f, 0x12, 0x77, 0xa3, 0xa7, + 0x7f, 0x51, 0x83, 0x81, 0x0a, 0xae, 0xa1, 0xa7, 0x62, 0xdb, 0xef, 0xbc, 0xba, 0xfd, 0x1e, 0xec, + 0x95, 0x47, 0x2a, 0xb8, 0xa6, 0x6c, 0xf4, 0x4f, 0x6b, 0x30, 0xd3, 0x70, 0x9d, 0xc0, 0xa0, 0xfd, + 0xc2, 0x5c, 0x0e, 0x95, 0x67, 0x5e, 0x21, 0xed, 0xb2, 0x92, 0x40, 0x16, 0x19, 0x45, 0x93, 0x10, + 0x1f, 0xa7, 0x29, 0x33, 0x95, 0xba, 0x62, 0xbb, 0x1d, 0x73, 0xcd, 0x73, 0x37, 0x2d, 0x9b, 0xbc, + 0x3d, 0x54, 0x6a, 0xb5, 0xc7, 0xc7, 0xab, 0x52, 0xc7, 0x28, 0x1d, 0xac, 0x52, 0xab, 0xd5, 0xdf, + 0x26, 0x2a, 0xb5, 0xda, 0xe5, 0x1c, 0xa9, 0xe9, 0x5b, 0xe1, 0xac, 0x5a, 0x2b, 0x32, 0x73, 0x5d, + 0x82, 0xc1, 0xbb, 0x96, 0x63, 0x26, 0x39, 0xef, 0x4d, 0xcb, 0x31, 0x31, 0x83, 0x84, 0xbc, 0xb9, + 0x94, 0xcb, 0x9b, 0xff, 0x6c, 0x24, 0x3e, 0x6d, 0x4c, 0x28, 0x7b, 0x02, 0x46, 0x1b, 0xc6, 0x62, + 0xc7, 0x31, 0xed, 0x90, 0xad, 0xd3, 0x29, 0xa8, 0x2c, 0xf0, 0x32, 0x1c, 0x42, 0xd1, 0x7d, 0x80, + 0xc8, 0xa2, 0xdc, 0xcf, 0x61, 0x17, 0x19, 0xab, 0xeb, 0x24, 0x08, 0x2c, 0xa7, 0xe9, 0x47, 0xfb, + 0x38, 0x82, 0x61, 0x85, 0x1a, 0xfa, 0x08, 0x4c, 0xaa, 0x27, 0x2f, 0x37, 0x6d, 0x15, 0x5c, 0x86, + 0xd8, 0x11, 0x7f, 0x56, 0x10, 0x9e, 0x54, 0x4b, 0x7d, 0x1c, 0xa7, 0x86, 0x76, 0x43, 0x39, 0x83, + 0x1b, 0xd6, 0x06, 0x8b, 0x4b, 0xce, 0xea, 0x11, 0x7f, 0x46, 0x10, 0x9f, 0x88, 0x19, 0xfa, 0x62, + 0xa4, 0x32, 0xac, 0x0e, 0x43, 0xc7, 0x65, 0x75, 0x20, 0x30, 0xc2, 0xed, 0x2e, 0xfe, 0xec, 0x30, + 0x1b, 0xe0, 0xd5, 0x22, 0x03, 0xe4, 0x26, 0x9c, 0xe8, 0x8a, 0x84, 0xff, 0xf6, 0xb1, 0xc4, 0x8d, + 0xb6, 0x61, 0x82, 0x0a, 0x90, 0x75, 0x62, 0x93, 0x46, 0xe0, 0x7a, 0xb3, 0x23, 0xc5, 0xaf, 0x20, + 0xea, 0x0a, 0x1e, 0x2e, 0xad, 0xa9, 0x25, 0x38, 0x46, 0x27, 0x34, 0x4b, 0x8d, 0xe6, 0x9a, 0xa5, + 0x3a, 0x30, 0xbe, 0xad, 0x98, 0x4f, 0xc7, 0xd8, 0x24, 0xbc, 0x58, 0xa4, 0x63, 0x91, 0x2d, 0x75, + 0xf1, 0xb4, 0x20, 0x34, 0xae, 0xda, 0x5d, 0x55, 0x3a, 0x68, 0x03, 0x46, 0x36, 0xb8, 0xac, 0x35, + 0x0b, 0x6c, 0x2e, 0x9e, 0xef, 0x43, 0x84, 0xe4, 0xf2, 0x9c, 0xf8, 0x81, 0x25, 0x62, 0xfd, 0xdf, + 0x96, 0x00, 0xa5, 0x39, 0x2c, 0xfa, 0x51, 0x0d, 0x50, 0xf4, 0x99, 0x09, 0x29, 0x90, 0x5f, 0x47, + 0x8c, 0x5f, 0xf9, 0x60, 0x91, 0x6e, 0x2c, 0xed, 0xb4, 0x2d, 0x8f, 0x99, 0x93, 0x39, 0x32, 0xc1, + 0xca, 0x43, 0x1d, 0xe4, 0x66, 0x8a, 0x1a, 0xce, 0xe8, 0x01, 0xfa, 0x09, 0x0d, 0xce, 0xa8, 0xdf, + 0x60, 0xd8, 0x35, 0xce, 0x7f, 0x57, 0xfa, 0xfd, 0xf0, 0xe3, 0xbd, 0xbb, 0x20, 0x7a, 0x77, 0x26, + 0xa3, 0x8a, 0x8f, 0x33, 0x3b, 0xa2, 0xff, 0xf8, 0x04, 0xcc, 0x54, 0xec, 0x8e, 0x1f, 0x10, 0x6f, + 0x41, 0x78, 0x35, 0x10, 0x0f, 0x7d, 0x5c, 0x83, 0x73, 0xec, 0xdf, 0xaa, 0x7b, 0xcf, 0xa9, 0x12, + 0xdb, 0xd8, 0x5d, 0xd8, 0xa4, 0x35, 0x4c, 0xf3, 0x70, 0x87, 0x52, 0xb5, 0x23, 0xd4, 0x4c, 0x66, + 0xbd, 0xaf, 0x67, 0x62, 0xc4, 0x39, 0x94, 0xd0, 0xf7, 0x6b, 0xf0, 0x50, 0x06, 0xa8, 0x4a, 0x6c, + 0x12, 0x48, 0xe1, 0xf9, 0xb0, 0xfd, 0x78, 0x64, 0x7f, 0xaf, 0xfc, 0x50, 0x3d, 0x0f, 0x29, 0xce, + 0xa7, 0x87, 0x7e, 0x50, 0x83, 0xb9, 0x0c, 0xe8, 0x35, 0xc3, 0xb2, 0x3b, 0x9e, 0x94, 0xab, 0x0f, + 0xdb, 0x1d, 0x26, 0xde, 0xd6, 0x73, 0xb1, 0xe2, 0x2e, 0x14, 0xd1, 0x47, 0xe1, 0x6c, 0x08, 0xbd, + 0xed, 0x38, 0x84, 0x98, 0x31, 0x29, 0xfb, 0xb0, 0x5d, 0x79, 0x68, 0x7f, 0xaf, 0x7c, 0xb6, 0x9e, + 0x85, 0x10, 0x67, 0xd3, 0x41, 0x4d, 0x78, 0x24, 0x02, 0x04, 0x96, 0x6d, 0xdd, 0xe7, 0x8a, 0xc0, + 0x96, 0x47, 0xfc, 0x2d, 0xd7, 0x36, 0x19, 0x8b, 0xd7, 0x16, 0xdf, 0xb9, 0xbf, 0x57, 0x7e, 0xa4, + 0xde, 0xad, 0x22, 0xee, 0x8e, 0x07, 0x99, 0x30, 0xe1, 0x37, 0x0c, 0xa7, 0xe6, 0x04, 0xc4, 0xdb, + 0x36, 0xec, 0xd9, 0xe1, 0x42, 0x03, 0xe4, 0x8c, 0x55, 0xc1, 0x83, 0x63, 0x58, 0xd1, 0xfb, 0x61, + 0x94, 0xec, 0xb4, 0x0d, 0xc7, 0x24, 0x9c, 0x99, 0x8f, 0x2d, 0x5e, 0xa0, 0x22, 0xc4, 0x92, 0x28, + 0x7b, 0xb0, 0x57, 0x9e, 0x90, 0xff, 0xaf, 0xb8, 0x26, 0xc1, 0x61, 0x6d, 0xf4, 0x61, 0xfa, 0x91, + 0xef, 0xac, 0xba, 0x26, 0x61, 0x47, 0x93, 0x2f, 0x75, 0xad, 0xd1, 0x42, 0xfd, 0x9c, 0xe5, 0x5f, + 0x70, 0x1a, 0x1f, 0xce, 0xa4, 0x42, 0x97, 0xa1, 0x65, 0xec, 0x5c, 0xf7, 0x8c, 0x06, 0xd9, 0xec, + 0xd8, 0xeb, 0xc4, 0x6b, 0x59, 0x0e, 0x37, 0x36, 0x90, 0x86, 0xeb, 0x98, 0xf4, 0x00, 0xd0, 0x9e, + 0x18, 0xe2, 0xcb, 0xb0, 0xd2, 0xad, 0x22, 0xee, 0x8e, 0x07, 0x3d, 0x03, 0x13, 0x56, 0xd3, 0x71, + 0x3d, 0xb2, 0x6e, 0x58, 0x4e, 0xe0, 0xcf, 0x02, 0xbb, 0x97, 0x63, 0xd3, 0x5a, 0x53, 0xca, 0x71, + 0xac, 0x16, 0xda, 0x06, 0xe4, 0x90, 0x7b, 0x6b, 0xae, 0xc9, 0xb6, 0xc0, 0xed, 0x36, 0xdb, 0xc8, + 0xb3, 0xe3, 0x85, 0xa6, 0x86, 0xa9, 0xa2, 0xab, 0x29, 0x6c, 0x38, 0x83, 0x02, 0xba, 0x06, 0xa8, + 0x65, 0xec, 0x2c, 0xb5, 0xda, 0xc1, 0xee, 0x62, 0xc7, 0xbe, 0x2b, 0xb8, 0xc6, 0x04, 0x9b, 0x0b, + 0x6e, 0xa8, 0x49, 0x41, 0x71, 0x46, 0x0b, 0x64, 0xc0, 0xc3, 0x7c, 0x3c, 0x55, 0x83, 0xb4, 0x5c, + 0xc7, 0x27, 0x81, 0xaf, 0x6c, 0xd2, 0xd9, 0x49, 0x76, 0xf9, 0xce, 0x14, 0xc3, 0x5a, 0x7e, 0x35, + 0xdc, 0x0d, 0x47, 0xdc, 0xfd, 0x68, 0xea, 0x00, 0xf7, 0xa3, 0x67, 0x61, 0xd2, 0x0f, 0x0c, 0x2f, + 0xe8, 0xb4, 0xc5, 0x32, 0x9c, 0x62, 0xcb, 0xc0, 0xec, 0x78, 0x75, 0x15, 0x80, 0xe3, 0xf5, 0xe8, + 0xf2, 0x71, 0xc5, 0x43, 0xb4, 0x9b, 0x8e, 0x96, 0xaf, 0xae, 0x94, 0xe3, 0x58, 0x2d, 0xfd, 0x7f, + 0x0d, 0xc2, 0x6c, 0xea, 0x7c, 0x90, 0x2e, 0x3b, 0x07, 0x72, 0x00, 0xed, 0x88, 0x38, 0x40, 0x1b, + 0x2e, 0x85, 0x15, 0xae, 0xb7, 0x3b, 0x99, 0xb4, 0x4a, 0x8c, 0xd6, 0x63, 0xfb, 0x7b, 0xe5, 0x4b, + 0xf5, 0x03, 0xea, 0xe2, 0x03, 0xb1, 0xe5, 0x73, 0xd7, 0x81, 0x13, 0xe2, 0xae, 0x1f, 0x86, 0x33, + 0x0a, 0xc0, 0x23, 0x86, 0xb9, 0xdb, 0x07, 0x77, 0x67, 0x4c, 0xa5, 0x9e, 0x81, 0x0f, 0x67, 0x52, + 0xc9, 0x65, 0x69, 0x43, 0x27, 0xc1, 0xd2, 0xf4, 0xbd, 0x01, 0x18, 0xab, 0xb8, 0x8e, 0x69, 0xb1, + 0xcf, 0xe3, 0xe9, 0xd8, 0x45, 0xec, 0x23, 0xaa, 0xc4, 0xfb, 0x60, 0xaf, 0x3c, 0x19, 0x56, 0x54, + 0x44, 0xe0, 0xe7, 0x42, 0x55, 0x9e, 0xeb, 0x91, 0xef, 0x8c, 0xab, 0xe0, 0x0f, 0xf6, 0xca, 0xa7, + 0xc2, 0x66, 0x71, 0xad, 0x9c, 0xf2, 0x2b, 0xdb, 0xf0, 0x83, 0x75, 0xcf, 0x70, 0x7c, 0xab, 0x0f, + 0xb3, 0x59, 0x28, 0x2a, 0x2e, 0xa7, 0xb0, 0xe1, 0x0c, 0x0a, 0xe8, 0x75, 0x98, 0xa2, 0xa5, 0xb7, + 0xdb, 0xa6, 0x11, 0x90, 0x82, 0xd6, 0xb2, 0xd0, 0x5b, 0x64, 0x39, 0x86, 0x09, 0x27, 0x30, 0xf3, + 0x8b, 0x6b, 0xc3, 0x77, 0x1d, 0xb6, 0x9e, 0xb1, 0x8b, 0x6b, 0x5a, 0x8a, 0x05, 0x14, 0x3d, 0x09, + 0x23, 0x2d, 0xe2, 0xfb, 0x46, 0x93, 0xb0, 0x33, 0x77, 0x2c, 0x52, 0x87, 0x56, 0x78, 0x31, 0x96, + 0x70, 0xf4, 0x6e, 0x18, 0x6a, 0xb8, 0x26, 0xf1, 0x67, 0x47, 0x18, 0x5b, 0xa1, 0x1c, 0x76, 0xa8, + 0x42, 0x0b, 0x1e, 0xec, 0x95, 0xc7, 0x98, 0x71, 0x9f, 0xfe, 0xc2, 0xbc, 0x92, 0xfe, 0x13, 0x1a, + 0x4c, 0x27, 0xcd, 0x4d, 0x3d, 0x5c, 0xb8, 0x9f, 0xdc, 0xdd, 0xb5, 0xfe, 0x19, 0x0d, 0x26, 0x68, + 0x0f, 0x3d, 0xd7, 0x5e, 0xb3, 0x0d, 0x87, 0xa0, 0xef, 0xd5, 0x60, 0x7a, 0xcb, 0x6a, 0x6e, 0xa9, + 0x1e, 0x33, 0x42, 0x18, 0x2e, 0x64, 0x92, 0xba, 0x91, 0xc0, 0xb5, 0x78, 0x66, 0x7f, 0xaf, 0x3c, + 0x9d, 0x2c, 0xc5, 0x29, 0x9a, 0xfa, 0x27, 0x4b, 0x70, 0x46, 0xf4, 0xcc, 0xa6, 0xd2, 0x69, 0xdb, + 0x76, 0x77, 0x5b, 0xc4, 0x39, 0x09, 0xe7, 0x16, 0xb9, 0x42, 0xa5, 0xdc, 0x15, 0x6a, 0xa5, 0x56, + 0x68, 0xa0, 0xc8, 0x0a, 0x85, 0x1b, 0xf9, 0x80, 0x55, 0xfa, 0x23, 0x0d, 0x66, 0xb3, 0xe6, 0xe2, + 0x04, 0x4c, 0x69, 0xad, 0xb8, 0x29, 0xed, 0x46, 0x51, 0x5b, 0x6c, 0xb2, 0xeb, 0x39, 0x26, 0xb5, + 0x3f, 0x2c, 0xc1, 0xb9, 0xa8, 0x7a, 0xcd, 0xf1, 0x03, 0xc3, 0xb6, 0xb9, 0xf8, 0x70, 0xfc, 0xeb, + 0xde, 0x8e, 0x59, 0x60, 0x57, 0xfb, 0x1b, 0xaa, 0xda, 0xf7, 0x5c, 0x5b, 0xec, 0x4e, 0xc2, 0x16, + 0xbb, 0x76, 0x84, 0x34, 0xbb, 0x5b, 0x65, 0xff, 0x9b, 0x06, 0x73, 0xd9, 0x0d, 0x4f, 0x60, 0x53, + 0xb9, 0xf1, 0x4d, 0xf5, 0xc1, 0xa3, 0x1b, 0x75, 0xce, 0xb6, 0xfa, 0xf9, 0x52, 0xde, 0x68, 0x99, + 0x59, 0x75, 0x13, 0x4e, 0x79, 0xa4, 0x69, 0xf9, 0x81, 0xb8, 0x67, 0x3d, 0x9c, 0x5b, 0xa4, 0xbc, + 0xda, 0x38, 0x85, 0xe3, 0x38, 0x70, 0x12, 0x29, 0x5a, 0x85, 0x11, 0x9f, 0x10, 0x93, 0xe2, 0x2f, + 0xf5, 0x8e, 0x3f, 0x3c, 0x8d, 0xea, 0xbc, 0x2d, 0x96, 0x48, 0xd0, 0xb7, 0xc1, 0xa4, 0x19, 0x7e, + 0x51, 0x07, 0x78, 0x1f, 0x25, 0xb1, 0x32, 0x49, 0xba, 0xaa, 0xb6, 0xc6, 0x71, 0x64, 0xfa, 0x9f, + 0x6b, 0x70, 0xa1, 0xdb, 0xde, 0x42, 0x6f, 0x00, 0x34, 0xa4, 0x78, 0x21, 0xcd, 0x50, 0x2f, 0x14, + 0x5c, 0x4b, 0x8e, 0x25, 0xfa, 0x40, 0xc3, 0x22, 0x1f, 0x2b, 0x44, 0x32, 0x9c, 0x9a, 0x4a, 0xc7, + 0xe4, 0xd4, 0xa4, 0xff, 0x77, 0x4d, 0x65, 0x45, 0xea, 0xda, 0xbe, 0xdd, 0x58, 0x91, 0xda, 0xf7, + 0x3c, 0x56, 0xa4, 0xff, 0x76, 0x09, 0x2e, 0x65, 0x37, 0x51, 0xce, 0xde, 0x0f, 0xc0, 0x70, 0x9b, + 0xbb, 0x2e, 0x0f, 0xb0, 0xb3, 0xf1, 0x09, 0xca, 0x59, 0xb8, 0x63, 0xf1, 0x83, 0xbd, 0xf2, 0x5c, + 0x16, 0xa3, 0x17, 0x2e, 0xc9, 0xa2, 0x1d, 0xb2, 0x12, 0xf6, 0x64, 0x2e, 0xfd, 0x7d, 0x53, 0x8f, + 0xcc, 0xc5, 0xd8, 0x20, 0x76, 0xcf, 0x26, 0xe4, 0x8f, 0x69, 0x30, 0x15, 0xdb, 0xd1, 0xfe, 0xec, + 0x10, 0xdb, 0xa3, 0x85, 0xfc, 0x49, 0x62, 0x9f, 0x4a, 0x74, 0x72, 0xc7, 0x8a, 0x7d, 0x9c, 0x20, + 0x98, 0x60, 0xb3, 0xea, 0xac, 0xbe, 0xed, 0xd8, 0xac, 0xda, 0xf9, 0x1c, 0x36, 0xfb, 0x63, 0xa5, + 0xbc, 0xd1, 0x32, 0x36, 0x7b, 0x0f, 0xc6, 0xe4, 0x23, 0x2c, 0xc9, 0x2e, 0xae, 0xf5, 0xdb, 0x27, + 0x8e, 0x2e, 0xf2, 0xa5, 0x94, 0x25, 0x3e, 0x8e, 0x68, 0xa1, 0xef, 0xd6, 0x00, 0xa2, 0x85, 0x11, + 0x1f, 0xd5, 0xfa, 0xd1, 0x4d, 0x87, 0x22, 0xd6, 0x4c, 0xd1, 0x4f, 0x5a, 0xd9, 0x14, 0x0a, 0x5d, + 0xfd, 0xcf, 0x06, 0x00, 0xa5, 0xfb, 0xde, 0xdb, 0x6d, 0xe1, 0x01, 0x02, 0xe9, 0x0b, 0x70, 0xaa, + 0x69, 0xbb, 0x1b, 0x86, 0x6d, 0xef, 0x8a, 0x57, 0x2e, 0xe2, 0xbd, 0xc4, 0x69, 0x7a, 0x30, 0x5d, + 0x8f, 0x83, 0x70, 0xb2, 0x2e, 0x6a, 0xc3, 0xb4, 0x47, 0x1a, 0xae, 0xd3, 0xb0, 0x6c, 0xa6, 0x3a, + 0xb9, 0x9d, 0xa0, 0xa0, 0x06, 0xce, 0xc4, 0x7b, 0x9c, 0xc0, 0x85, 0x53, 0xd8, 0xd1, 0xe3, 0x30, + 0xd2, 0xf6, 0xac, 0x96, 0xe1, 0xed, 0x32, 0xe5, 0x6c, 0x94, 0xdf, 0x84, 0xac, 0xf1, 0x22, 0x2c, + 0x61, 0xe8, 0xc3, 0x30, 0x66, 0x5b, 0x9b, 0xa4, 0xb1, 0xdb, 0xb0, 0x89, 0x30, 0x88, 0xde, 0x3a, + 0x9a, 0x2d, 0xb3, 0x2c, 0xd1, 0x0a, 0x3f, 0x2d, 0xf9, 0x13, 0x47, 0x04, 0x51, 0x0d, 0x4e, 0xdf, + 0x73, 0xbd, 0xbb, 0xc4, 0xb3, 0x89, 0xef, 0xd7, 0x3b, 0xed, 0xb6, 0xeb, 0x05, 0xc4, 0x64, 0x66, + 0xd3, 0x51, 0xfe, 0x94, 0xe7, 0x4e, 0x1a, 0x8c, 0xb3, 0xda, 0xe8, 0x9f, 0x2a, 0xc1, 0xc3, 0x5d, + 0x3a, 0x81, 0x30, 0xfd, 0x36, 0xc4, 0x1c, 0x89, 0x9d, 0xf0, 0x0c, 0xdf, 0xcf, 0xa2, 0xf0, 0xc1, + 0x5e, 0xf9, 0xd1, 0x2e, 0x08, 0xea, 0x74, 0x2b, 0x92, 0xe6, 0x2e, 0x8e, 0xd0, 0xa0, 0x1a, 0x0c, + 0x9b, 0xd1, 0x2d, 0xc2, 0xd8, 0xe2, 0xd3, 0x94, 0x5b, 0x73, 0x7b, 0x5f, 0xaf, 0xd8, 0x04, 0x02, + 0xb4, 0x0c, 0x23, 0xdc, 0xbb, 0x8b, 0x08, 0xce, 0x7f, 0x85, 0xa9, 0xc7, 0xbc, 0xa8, 0x57, 0x64, + 0x12, 0x85, 0xfe, 0xa7, 0x1a, 0x8c, 0x54, 0x5c, 0x8f, 0x54, 0x57, 0xeb, 0x68, 0x17, 0xc6, 0x95, + 0x77, 0xa6, 0x82, 0x0b, 0x16, 0x64, 0x0b, 0x0c, 0xe3, 0x42, 0x84, 0x4d, 0xbe, 0x8c, 0x09, 0x0b, + 0xb0, 0x4a, 0x0b, 0xbd, 0x41, 0xe7, 0xfc, 0x9e, 0x67, 0x05, 0x94, 0x70, 0x3f, 0x6e, 0x17, 0x9c, + 0x30, 0x96, 0xb8, 0xf8, 0x8e, 0x0a, 0x7f, 0xe2, 0x88, 0x8a, 0xbe, 0x46, 0x39, 0x40, 0xb2, 0x9b, + 0xe8, 0x2a, 0x0c, 0xb6, 0x5c, 0x53, 0xae, 0xfb, 0xbb, 0xe4, 0xf7, 0xbd, 0xe2, 0x9a, 0x74, 0x6e, + 0xcf, 0xa5, 0x5b, 0x30, 0xcb, 0x3c, 0x6b, 0xa3, 0xaf, 0xc2, 0x74, 0x92, 0x3e, 0xba, 0x0a, 0x53, + 0x0d, 0xb7, 0xd5, 0x72, 0x9d, 0x7a, 0x67, 0x73, 0xd3, 0xda, 0x21, 0xb1, 0x27, 0x4b, 0x95, 0x18, + 0x04, 0x27, 0x6a, 0xea, 0x9f, 0xd3, 0x60, 0x80, 0xae, 0x8b, 0x0e, 0xc3, 0xa6, 0xdb, 0x32, 0x2c, + 0x47, 0xf4, 0x8a, 0x3d, 0xcf, 0xaa, 0xb2, 0x12, 0x2c, 0x20, 0xa8, 0x0d, 0x63, 0x52, 0x68, 0xea, + 0xcb, 0x41, 0xb5, 0xba, 0x5a, 0x0f, 0x9d, 0xfa, 0x43, 0x4e, 0x2e, 0x4b, 0x7c, 0x1c, 0x11, 0xd1, + 0x0d, 0x98, 0xa9, 0xae, 0xd6, 0x6b, 0x4e, 0xc3, 0xee, 0x98, 0x64, 0x69, 0x87, 0xfd, 0xa1, 0xbc, + 0xc4, 0xe2, 0x25, 0x62, 0x9c, 0x8c, 0x97, 0x88, 0x4a, 0x58, 0xc2, 0x68, 0x35, 0xc2, 0x5b, 0x88, + 0x17, 0x3c, 0xac, 0x9a, 0x40, 0x82, 0x25, 0x4c, 0xff, 0x4a, 0x09, 0xc6, 0x95, 0x0e, 0x21, 0x1b, + 0x46, 0xf8, 0x70, 0xfd, 0x7e, 0x5e, 0x69, 0xa6, 0x7a, 0xcd, 0xa9, 0xf3, 0x09, 0xf5, 0xb1, 0x24, + 0xa1, 0xf2, 0xc5, 0x52, 0x17, 0xbe, 0x38, 0x1f, 0x7b, 0x08, 0xc5, 0x3f, 0xc9, 0xa9, 0xfc, 0x47, + 0x50, 0xe8, 0x82, 0x38, 0x41, 0xb8, 0x87, 0xe8, 0x68, 0xe2, 0xf4, 0xd8, 0x84, 0xa1, 0xfb, 0xae, + 0x43, 0x7c, 0x61, 0xf7, 0x3c, 0xa2, 0x01, 0x8e, 0x51, 0xf9, 0xe0, 0x55, 0x8a, 0x17, 0x73, 0xf4, + 0xfa, 0x4f, 0x6a, 0x00, 0x55, 0x23, 0x30, 0xf8, 0xe5, 0x7a, 0x0f, 0xfe, 0x8f, 0x17, 0x62, 0x07, + 0xdf, 0x68, 0xea, 0x61, 0xca, 0xa0, 0x6f, 0xdd, 0x97, 0xc3, 0x0f, 0x05, 0x6a, 0x8e, 0xbd, 0x6e, + 0xdd, 0x27, 0x98, 0xc1, 0xd1, 0x53, 0x30, 0x46, 0x9c, 0x86, 0xb7, 0xdb, 0xa6, 0xcc, 0x7b, 0x90, + 0xcd, 0x2a, 0xfb, 0x42, 0x97, 0x64, 0x21, 0x8e, 0xe0, 0xfa, 0xd3, 0x10, 0xd7, 0x8a, 0x7a, 0x70, + 0xa3, 0xfc, 0x0b, 0x0d, 0xce, 0x57, 0x3b, 0x86, 0xbd, 0xd0, 0xa6, 0x1b, 0xd5, 0xb0, 0xaf, 0xb9, + 0xfc, 0x36, 0x95, 0xaa, 0x0a, 0xef, 0x86, 0x51, 0x29, 0x87, 0x08, 0x0c, 0xa1, 0xc4, 0x26, 0x19, + 0x25, 0x0e, 0x6b, 0x20, 0x03, 0x46, 0x7d, 0x29, 0x19, 0x97, 0xfa, 0x90, 0x8c, 0x25, 0x89, 0x50, + 0x32, 0x0e, 0xd1, 0x22, 0x0c, 0xe7, 0xc4, 0x07, 0x51, 0x27, 0xde, 0xb6, 0xd5, 0x20, 0x0b, 0x8d, + 0x86, 0xdb, 0x71, 0x02, 0x5f, 0x08, 0x0c, 0xec, 0x0a, 0xbb, 0x96, 0x59, 0x03, 0xe7, 0xb4, 0xd4, + 0xbf, 0x3a, 0x08, 0x0f, 0x2d, 0xad, 0x57, 0xaa, 0x62, 0x42, 0x2d, 0xd7, 0xb9, 0x49, 0x76, 0xff, + 0xda, 0xad, 0xf4, 0xaf, 0xdd, 0x4a, 0x8f, 0xd0, 0xad, 0xf4, 0x25, 0x98, 0x8e, 0xb6, 0x97, 0xf0, + 0x81, 0x7a, 0x2a, 0xa9, 0x50, 0x8c, 0xc9, 0xa3, 0x37, 0xad, 0x04, 0xe8, 0xff, 0xa3, 0x04, 0xd3, + 0x49, 0x7f, 0x17, 0xf4, 0x64, 0xe4, 0x60, 0xad, 0xc5, 0x4d, 0xff, 0x49, 0x27, 0x6b, 0xb4, 0x09, + 0x53, 0x84, 0x35, 0x67, 0x12, 0xbf, 0x11, 0x14, 0xd9, 0x81, 0xfc, 0xcd, 0x70, 0x0c, 0x0b, 0x4e, + 0x60, 0x45, 0x75, 0x98, 0x6a, 0xd8, 0x86, 0xef, 0x5b, 0x9b, 0x56, 0x23, 0x7a, 0x18, 0x30, 0xb6, + 0xf8, 0x14, 0x3b, 0xbc, 0x63, 0x90, 0x07, 0x7b, 0xe5, 0xb3, 0xa2, 0x9f, 0x71, 0x00, 0x4e, 0xa0, + 0x40, 0xbe, 0x2a, 0x47, 0x73, 0x87, 0xb8, 0xc5, 0x42, 0xaf, 0x1b, 0x22, 0xa1, 0xce, 0x68, 0x2a, + 0x6a, 0x57, 0x96, 0xf8, 0xac, 0xff, 0x9c, 0x06, 0xe7, 0xb2, 0x3d, 0x8c, 0x0e, 0x37, 0xef, 0xa7, + 0xe3, 0x83, 0xa1, 0x28, 0xe4, 0x91, 0xf0, 0x8c, 0x68, 0x76, 0xba, 0x92, 0xae, 0x92, 0x3f, 0x3b, + 0x59, 0x08, 0xf5, 0xb7, 0x4a, 0x30, 0xb9, 0xb4, 0xd3, 0x76, 0xfd, 0x8e, 0x47, 0x58, 0xfd, 0x13, + 0x30, 0xf3, 0x3c, 0x09, 0x23, 0x5b, 0x86, 0x63, 0xda, 0xc4, 0x13, 0xe3, 0x09, 0xa7, 0xe1, 0x06, + 0x2f, 0xc6, 0x12, 0x8e, 0xde, 0x04, 0xf0, 0x1b, 0x5b, 0xc4, 0xec, 0x30, 0x31, 0x99, 0x33, 0xa2, + 0x9b, 0x05, 0x7d, 0xbe, 0xa2, 0x31, 0xd6, 0x43, 0x94, 0x42, 0x7c, 0x08, 0x7f, 0x63, 0x85, 0x9c, + 0xfe, 0xbb, 0x1a, 0xcc, 0xc4, 0xda, 0x9d, 0x80, 0xf5, 0x62, 0x33, 0x6e, 0xbd, 0x58, 0xe8, 0x7b, + 0xac, 0x39, 0x46, 0x8b, 0x4f, 0x94, 0xe0, 0x7c, 0xce, 0x9c, 0xa4, 0xbc, 0x1f, 0xb5, 0x13, 0xf2, + 0x7e, 0xec, 0xc0, 0x78, 0xe0, 0xda, 0xe2, 0x89, 0x8f, 0x9c, 0x81, 0x42, 0xbe, 0x8d, 0xeb, 0x21, + 0x9a, 0xc8, 0xb7, 0x31, 0x2a, 0xf3, 0xb1, 0x4a, 0x47, 0xff, 0xa2, 0x06, 0x63, 0xa1, 0x91, 0xf4, + 0xeb, 0xea, 0xa2, 0xb2, 0xf7, 0x48, 0x10, 0xfa, 0xaf, 0x95, 0x28, 0xd7, 0x11, 0xb8, 0xe5, 0x49, + 0xc0, 0x3e, 0xf1, 0x1e, 0x2c, 0x2d, 0x17, 0x62, 0x7e, 0xd9, 0xa3, 0xe9, 0xe7, 0x38, 0xed, 0x8e, + 0xd7, 0x76, 0x7d, 0x29, 0x73, 0x72, 0xe1, 0x9c, 0x17, 0x61, 0x09, 0x43, 0xab, 0x30, 0xe4, 0x33, + 0x1e, 0x35, 0x58, 0x64, 0x36, 0x98, 0xd8, 0xcc, 0xfa, 0x8b, 0x39, 0x1a, 0xf4, 0xa6, 0x7a, 0xcc, + 0x0d, 0x15, 0xb7, 0xe5, 0xd1, 0x91, 0x98, 0xa1, 0xd4, 0x99, 0x7e, 0x87, 0x9c, 0x79, 0x6c, 0x2e, + 0xc3, 0xb4, 0x70, 0xc5, 0xe3, 0xdb, 0xc6, 0x69, 0x10, 0xf4, 0xfe, 0xd8, 0xce, 0x78, 0x2c, 0xe1, + 0xaa, 0x70, 0x26, 0x59, 0x3f, 0xda, 0x31, 0xba, 0x0f, 0xa3, 0xd7, 0x45, 0x27, 0xd1, 0x1c, 0x94, + 0x2c, 0xb9, 0x16, 0x20, 0x70, 0x94, 0x6a, 0x55, 0x5c, 0xb2, 0x7a, 0xf0, 0x8f, 0x57, 0x4f, 0x90, + 0x81, 0xee, 0x27, 0x88, 0xfe, 0x07, 0x25, 0x38, 0x23, 0xa9, 0xca, 0x31, 0x56, 0xc5, 0x45, 0xef, + 0x01, 0x0a, 0xc8, 0xc1, 0x96, 0xb7, 0x5b, 0x30, 0xc8, 0x18, 0x60, 0xa1, 0x0b, 0xe0, 0x10, 0x21, + 0xed, 0x0e, 0x66, 0x88, 0xd0, 0x87, 0x61, 0xd8, 0xa6, 0xd2, 0xbc, 0x74, 0x5c, 0x2f, 0x64, 0xa7, + 0xcc, 0x1a, 0x2e, 0x57, 0x12, 0x44, 0x10, 0x9e, 0xf0, 0x5e, 0x90, 0x17, 0x62, 0x41, 0x73, 0xee, + 0x39, 0x18, 0x57, 0xaa, 0x1d, 0x2a, 0x02, 0xcf, 0xe7, 0x4a, 0x30, 0x7b, 0x83, 0xd8, 0xad, 0xcc, + 0x5b, 0xfb, 0x32, 0x0c, 0x35, 0xb6, 0x0c, 0x8f, 0x07, 0x77, 0x9a, 0xe0, 0x9b, 0xbc, 0x42, 0x0b, + 0x30, 0x2f, 0x47, 0x1b, 0x30, 0xcc, 0x50, 0xc9, 0x1b, 0x9d, 0x17, 0x95, 0x99, 0x8c, 0xa2, 0x7e, + 0x7d, 0x47, 0x18, 0x16, 0x2c, 0x1a, 0x78, 0xac, 0x02, 0x3d, 0x5e, 0x3e, 0x58, 0xbf, 0xb5, 0xca, + 0xed, 0x15, 0x2f, 0x33, 0x8c, 0x58, 0x60, 0x46, 0xf7, 0x61, 0xd2, 0x6d, 0x58, 0x98, 0xb4, 0x5d, + 0xdf, 0x0a, 0x5c, 0x6f, 0x57, 0x2c, 0x5a, 0xa1, 0xa3, 0xe5, 0x56, 0xa5, 0x16, 0x21, 0xe2, 0xb7, + 0x69, 0xb1, 0x22, 0x1c, 0x27, 0xa5, 0x7f, 0x41, 0x83, 0xf1, 0x1b, 0xd6, 0x06, 0xf1, 0xb8, 0xb7, + 0x21, 0xb3, 0x46, 0xc4, 0xc2, 0x14, 0x8d, 0x67, 0x85, 0x28, 0x42, 0x3b, 0x30, 0x26, 0xce, 0xe1, + 0xf0, 0x3d, 0xd4, 0xf5, 0x62, 0x7e, 0x18, 0x21, 0x69, 0x71, 0xbe, 0xa9, 0x01, 0x08, 0x24, 0x05, + 0x1c, 0x11, 0xd3, 0xdf, 0x84, 0xd3, 0x19, 0x8d, 0xe8, 0x42, 0x32, 0x87, 0x3b, 0xf1, 0xd1, 0x48, + 0x6e, 0x45, 0x17, 0x92, 0x95, 0xa3, 0x87, 0x60, 0x80, 0x38, 0xa6, 0xf8, 0x62, 0x46, 0xf6, 0xf7, + 0xca, 0x03, 0x4b, 0x8e, 0x89, 0x69, 0x19, 0x65, 0xe2, 0xb6, 0x1b, 0x13, 0x6a, 0x19, 0x13, 0x5f, + 0x16, 0x65, 0x38, 0x84, 0x32, 0xcf, 0x99, 0xa4, 0x93, 0x08, 0xd5, 0x8f, 0xa6, 0x37, 0x13, 0xbc, + 0xa5, 0x1f, 0xdf, 0x94, 0x24, 0x9f, 0x5a, 0x9c, 0x15, 0x13, 0x92, 0xe2, 0x78, 0x38, 0x45, 0x57, + 0xff, 0xa5, 0x41, 0x78, 0xe4, 0x86, 0xeb, 0x59, 0xf7, 0x5d, 0x27, 0x30, 0xec, 0x35, 0xd7, 0x8c, + 0xfc, 0x06, 0xc5, 0x91, 0xf5, 0x3d, 0x1a, 0x9c, 0x6f, 0xb4, 0x3b, 0x5c, 0xbf, 0x92, 0xae, 0x77, + 0x6b, 0xc4, 0xb3, 0xdc, 0xa2, 0xee, 0xe5, 0x2c, 0xe4, 0x4c, 0x65, 0xed, 0x76, 0x16, 0x4a, 0x9c, + 0x47, 0x8b, 0x79, 0xb9, 0x9b, 0xee, 0x3d, 0x87, 0x75, 0xae, 0x1e, 0xb0, 0xd9, 0xbc, 0x1f, 0x2d, + 0x42, 0x41, 0x2f, 0xf7, 0x6a, 0x26, 0x46, 0x9c, 0x43, 0x09, 0x7d, 0x14, 0xce, 0x5a, 0xbc, 0x73, + 0x98, 0x18, 0xa6, 0xe5, 0x10, 0xdf, 0xe7, 0x2e, 0xb2, 0x7d, 0xb8, 0x71, 0xd7, 0xb2, 0x10, 0xe2, + 0x6c, 0x3a, 0xe8, 0x35, 0x00, 0x7f, 0xd7, 0x69, 0x88, 0xf9, 0x2f, 0xe6, 0xe0, 0xc7, 0x45, 0xe4, + 0x10, 0x0b, 0x56, 0x30, 0x52, 0x5d, 0x34, 0x08, 0x37, 0xe5, 0x30, 0x73, 0xd2, 0x64, 0xba, 0x68, + 0xb4, 0x87, 0x22, 0xb8, 0xfe, 0x8f, 0x34, 0x18, 0x11, 0xc1, 0xb6, 0xd0, 0xbb, 0x12, 0x86, 0xd6, + 0x90, 0x33, 0x27, 0x8c, 0xad, 0xbb, 0xec, 0xb6, 0x5d, 0x70, 0x56, 0xc1, 0x24, 0x0b, 0x59, 0xea, + 0x04, 0xe1, 0x88, 0x4d, 0xc7, 0x6e, 0xdd, 0xa5, 0x15, 0x5f, 0x21, 0xa6, 0x7f, 0x5e, 0x83, 0x99, + 0x54, 0xab, 0x1e, 0xa4, 0xa9, 0x13, 0x74, 0x64, 0xfb, 0xed, 0x41, 0x98, 0x62, 0x3e, 0xee, 0x8e, + 0x61, 0x73, 0x1b, 0xe8, 0x09, 0xa8, 0x6f, 0x4f, 0xc1, 0x98, 0xd5, 0x6a, 0x75, 0x02, 0xca, 0xaa, + 0xc5, 0x35, 0x16, 0x5b, 0xf3, 0x9a, 0x2c, 0xc4, 0x11, 0x1c, 0x39, 0x42, 0x50, 0xe0, 0x4c, 0x7c, + 0xb9, 0xd8, 0xca, 0xa9, 0x03, 0x9c, 0xa7, 0x87, 0x3a, 0x3f, 0xcd, 0xb3, 0xe4, 0x88, 0xef, 0xd5, + 0x00, 0xfc, 0xc0, 0xb3, 0x9c, 0x26, 0x2d, 0x14, 0xc2, 0x04, 0x3e, 0x02, 0xb2, 0xf5, 0x10, 0x29, + 0x27, 0x1e, 0x05, 0xe0, 0x0a, 0x01, 0x58, 0xa1, 0x8c, 0x16, 0x84, 0x0c, 0xc5, 0x39, 0xfe, 0x7b, + 0x12, 0xd2, 0xe2, 0x23, 0xe9, 0x28, 0xa2, 0x22, 0xd4, 0x49, 0x24, 0x64, 0xcd, 0x3d, 0x0b, 0x63, + 0x21, 0xbd, 0x83, 0x64, 0x92, 0x09, 0x45, 0x26, 0x99, 0x7b, 0x01, 0x4e, 0x25, 0xba, 0x7b, 0x28, + 0x91, 0xe6, 0x3f, 0x68, 0x80, 0xe2, 0xa3, 0x3f, 0x01, 0xc5, 0xb7, 0x19, 0x57, 0x7c, 0x17, 0xfb, + 0x5f, 0xb2, 0x1c, 0xcd, 0xf7, 0x67, 0x67, 0x80, 0xc5, 0x22, 0x0c, 0x63, 0x73, 0x8a, 0x83, 0x8b, + 0x9e, 0xb3, 0xd1, 0x2b, 0x2f, 0xf1, 0xe5, 0xf6, 0x71, 0xce, 0xde, 0x4c, 0xe0, 0x8a, 0xce, 0xd9, + 0x24, 0x04, 0xa7, 0xe8, 0xa2, 0x4f, 0x6a, 0x30, 0x6d, 0xc4, 0x63, 0x11, 0xca, 0x99, 0x29, 0x14, + 0x55, 0x26, 0x11, 0xd7, 0x30, 0xea, 0x4b, 0x02, 0xe0, 0xe3, 0x14, 0x59, 0xf4, 0x0c, 0x4c, 0x18, + 0x6d, 0x6b, 0xa1, 0x63, 0x5a, 0x54, 0x71, 0x92, 0x21, 0xdb, 0x98, 0x32, 0xbf, 0xb0, 0x56, 0x0b, + 0xcb, 0x71, 0xac, 0x56, 0x18, 0xf4, 0x4f, 0x4c, 0xe4, 0x60, 0x9f, 0x41, 0xff, 0xc4, 0x1c, 0x46, + 0x41, 0xff, 0xc4, 0xd4, 0xa9, 0x44, 0x90, 0x03, 0xe0, 0x5a, 0x66, 0x43, 0x90, 0x1c, 0x16, 0x12, + 0x75, 0x11, 0x31, 0xb7, 0x56, 0xad, 0x08, 0x8a, 0xec, 0xf4, 0x8b, 0x7e, 0x63, 0x85, 0x02, 0xfa, + 0x8c, 0x06, 0x93, 0x82, 0x77, 0x0b, 0x9a, 0x23, 0x6c, 0x89, 0x5e, 0x2d, 0xba, 0x5f, 0x12, 0x7b, + 0x72, 0x1e, 0xab, 0xc8, 0x39, 0xdf, 0x09, 0x5f, 0x03, 0xc7, 0x60, 0x38, 0xde, 0x0f, 0xf4, 0xa3, + 0x1a, 0x9c, 0xf1, 0x63, 0xf7, 0x15, 0xa2, 0x83, 0xa3, 0xc5, 0xa3, 0x91, 0xd5, 0x33, 0xf0, 0x89, + 0xb7, 0x07, 0x19, 0x10, 0x9c, 0x49, 0x9f, 0x8a, 0x65, 0xa7, 0xee, 0x19, 0x41, 0x63, 0xab, 0x62, + 0x34, 0xb6, 0xd8, 0x75, 0x15, 0x7f, 0xc3, 0x54, 0x70, 0x5f, 0xdf, 0x89, 0xa3, 0xe2, 0x8e, 0x1f, + 0x89, 0x42, 0x9c, 0x24, 0x88, 0x5c, 0x18, 0xf5, 0x44, 0x40, 0x5e, 0xf1, 0x9c, 0xb5, 0x58, 0x0c, + 0xda, 0x64, 0x74, 0x5f, 0x2e, 0xd8, 0xcb, 0x5f, 0x38, 0x24, 0x82, 0x9a, 0xf0, 0x08, 0x57, 0x6d, + 0x16, 0x1c, 0xd7, 0xd9, 0x6d, 0xb9, 0x1d, 0x7f, 0xa1, 0x13, 0x6c, 0x11, 0x27, 0x90, 0xc6, 0xee, + 0x71, 0x76, 0x8c, 0xb2, 0xb7, 0x34, 0x4b, 0xdd, 0x2a, 0xe2, 0xee, 0x78, 0xd0, 0x2b, 0x30, 0x4a, + 0xb6, 0x89, 0x13, 0xac, 0xaf, 0x2f, 0xb3, 0xe7, 0x50, 0x87, 0x97, 0xf6, 0xd8, 0x10, 0x96, 0x04, + 0x0e, 0x1c, 0x62, 0x43, 0x77, 0x61, 0xc4, 0xe6, 0x11, 0x95, 0xd9, 0xb3, 0xa8, 0x82, 0x4c, 0x31, + 0x19, 0x9d, 0x99, 0xeb, 0x7f, 0xe2, 0x07, 0x96, 0x14, 0x50, 0x1b, 0x2e, 0x99, 0x64, 0xd3, 0xe8, + 0xd8, 0xc1, 0xaa, 0x1b, 0x60, 0xf6, 0x70, 0x25, 0x34, 0xd8, 0xc9, 0x97, 0x6f, 0x53, 0x2c, 0x70, + 0x10, 0x7b, 0x12, 0x54, 0x3d, 0xa0, 0x2e, 0x3e, 0x10, 0x1b, 0xda, 0x85, 0x47, 0x45, 0x1d, 0xf6, + 0x52, 0xa6, 0xb1, 0x45, 0x67, 0x39, 0x4d, 0xf4, 0x14, 0x23, 0xfa, 0x37, 0xf6, 0xf7, 0xca, 0x8f, + 0x56, 0x0f, 0xae, 0x8e, 0x7b, 0xc1, 0xc9, 0x1e, 0x1f, 0x90, 0xc4, 0x25, 0xcf, 0xec, 0x74, 0xf1, + 0x39, 0x4e, 0x5e, 0x18, 0x71, 0xef, 0xa4, 0x64, 0x29, 0x4e, 0xd1, 0x44, 0x3f, 0xa3, 0xc1, 0xac, + 0x1f, 0x78, 0x9d, 0x46, 0xd0, 0xf1, 0x88, 0x99, 0xd8, 0xa1, 0x33, 0xac, 0x43, 0x85, 0x04, 0xb8, + 0x7a, 0x0e, 0x4e, 0xf6, 0x06, 0x73, 0x36, 0x0f, 0x8a, 0x73, 0xfb, 0x82, 0xfe, 0x9e, 0x06, 0xe7, + 0xe3, 0x40, 0xaa, 0x92, 0xf2, 0x7e, 0xa2, 0xe2, 0x77, 0x04, 0xf5, 0x6c, 0x94, 0x5c, 0x01, 0xcd, + 0x01, 0xe2, 0xbc, 0x8e, 0xcc, 0x7d, 0x00, 0x50, 0x9a, 0x7d, 0x1f, 0x24, 0x87, 0x8d, 0xaa, 0x72, + 0xd8, 0x67, 0x87, 0xe0, 0x61, 0x7a, 0x2a, 0x44, 0xda, 0xc7, 0x8a, 0xe1, 0x18, 0xcd, 0xaf, 0x4f, + 0x89, 0xe5, 0x0b, 0x1a, 0x9c, 0xdf, 0xca, 0xb6, 0x0c, 0x08, 0xfd, 0xe7, 0x43, 0x85, 0x2c, 0x38, + 0xdd, 0x8c, 0x0d, 0x9c, 0x61, 0x76, 0xad, 0x82, 0xf3, 0x3a, 0x85, 0x3e, 0x00, 0xd3, 0x8e, 0x6b, + 0x92, 0x4a, 0xad, 0x8a, 0x57, 0x0c, 0xff, 0x6e, 0x5d, 0xfa, 0x54, 0x0c, 0xf1, 0xef, 0x65, 0x35, + 0x01, 0xc3, 0xa9, 0xda, 0x68, 0x1b, 0x50, 0xdb, 0x35, 0x97, 0xb6, 0x79, 0xe4, 0xef, 0xfe, 0x3c, + 0x08, 0xd9, 0x8d, 0xf9, 0x5a, 0x0a, 0x1b, 0xce, 0xa0, 0xc0, 0x4c, 0x1b, 0xb4, 0x33, 0x2b, 0xae, + 0x63, 0x05, 0xae, 0xc7, 0x5e, 0xf5, 0xf6, 0xa5, 0xe1, 0x33, 0xd3, 0xc6, 0x6a, 0x26, 0x46, 0x9c, + 0x43, 0x49, 0xff, 0x9f, 0x1a, 0x9c, 0xa2, 0xdb, 0x62, 0xcd, 0x73, 0x77, 0x76, 0xbf, 0x1e, 0x37, + 0xe4, 0x93, 0xc2, 0xbd, 0x8c, 0x9b, 0xe4, 0xce, 0x2a, 0xae, 0x65, 0x63, 0xac, 0xcf, 0x91, 0x37, + 0x99, 0x6a, 0x95, 0x1c, 0xc8, 0xb7, 0x4a, 0xea, 0x9f, 0x29, 0x71, 0xcd, 0x41, 0x5a, 0x05, 0xbf, + 0x2e, 0xbf, 0xc3, 0x67, 0x61, 0x92, 0x96, 0xad, 0x18, 0x3b, 0x6b, 0xd5, 0x97, 0x5d, 0x5b, 0x3e, + 0x92, 0x64, 0xa6, 0xda, 0x9b, 0x2a, 0x00, 0xc7, 0xeb, 0xa1, 0xab, 0x30, 0xd2, 0xe6, 0x81, 0x37, + 0x84, 0xce, 0x7a, 0x89, 0xfb, 0x60, 0xb1, 0xa2, 0x07, 0x7b, 0xe5, 0x99, 0xe8, 0x86, 0x50, 0x86, + 0xfe, 0x91, 0x0d, 0xf4, 0xbf, 0x3c, 0x0d, 0x0c, 0xb9, 0x4d, 0x82, 0xaf, 0xc7, 0x39, 0x79, 0x1a, + 0xc6, 0x1b, 0xed, 0x4e, 0xe5, 0x5a, 0xfd, 0x43, 0x1d, 0x97, 0xd9, 0x22, 0x58, 0x80, 0x7c, 0xaa, + 0x4a, 0x54, 0xd6, 0x6e, 0xcb, 0x62, 0xac, 0xd6, 0xa1, 0xdc, 0xa1, 0xd1, 0xee, 0x08, 0x7e, 0xbb, + 0xa6, 0x7a, 0xff, 0x33, 0xee, 0x50, 0x59, 0xbb, 0x1d, 0x83, 0xe1, 0x54, 0x6d, 0xf4, 0x51, 0x98, + 0x20, 0xe2, 0xc3, 0xbd, 0x61, 0x78, 0xa6, 0xe0, 0x0b, 0xb5, 0xa2, 0x83, 0x0f, 0xa7, 0x56, 0x72, + 0x03, 0xae, 0x81, 0x2d, 0x29, 0x24, 0x70, 0x8c, 0x20, 0xfa, 0x56, 0x78, 0x48, 0xfe, 0xa6, 0xab, + 0xec, 0x9a, 0x49, 0x46, 0x31, 0xc4, 0x23, 0x66, 0x2c, 0xe5, 0x55, 0xc2, 0xf9, 0xed, 0xd1, 0xcf, + 0x69, 0x70, 0x2e, 0x84, 0x5a, 0x8e, 0xd5, 0xea, 0xb4, 0x30, 0x69, 0xd8, 0x86, 0xd5, 0x12, 0x7a, + 0xd7, 0x9d, 0x23, 0x1b, 0x68, 0x1c, 0x3d, 0x67, 0x56, 0xd9, 0x30, 0x9c, 0xd3, 0x25, 0xf4, 0x79, + 0x0d, 0x2e, 0x49, 0xd0, 0x9a, 0x47, 0x7c, 0xbf, 0xe3, 0x91, 0xe8, 0x89, 0xae, 0x98, 0x92, 0x91, + 0x42, 0xbc, 0x93, 0x09, 0xa0, 0x4b, 0x07, 0xe0, 0xc6, 0x07, 0x52, 0x57, 0xb7, 0x4b, 0xdd, 0xdd, + 0x0c, 0x84, 0xa2, 0x76, 0x5c, 0xdb, 0x85, 0x92, 0xc0, 0x31, 0x82, 0xe8, 0x1f, 0x6b, 0x70, 0x5e, + 0x2d, 0x50, 0x77, 0x0b, 0xd7, 0xd0, 0x5e, 0x39, 0xb2, 0xce, 0x24, 0xf0, 0x73, 0x09, 0x2b, 0x07, + 0x88, 0xf3, 0x7a, 0x45, 0xd9, 0x76, 0x8b, 0x6d, 0x4c, 0xae, 0xc5, 0x0d, 0x71, 0xb6, 0xcd, 0xf7, + 0xaa, 0x8f, 0x25, 0x0c, 0x3d, 0x03, 0x13, 0x6d, 0xd7, 0x5c, 0xb3, 0x4c, 0x7f, 0xd9, 0x6a, 0x59, + 0x01, 0xd3, 0xb5, 0x06, 0xf8, 0x74, 0xac, 0xb9, 0xe6, 0x5a, 0xad, 0xca, 0xcb, 0x71, 0xac, 0x16, + 0x9a, 0x07, 0xd8, 0x34, 0x2c, 0xbb, 0x7e, 0xcf, 0x68, 0xdf, 0x92, 0x91, 0x20, 0x98, 0x2d, 0xe0, + 0x5a, 0x58, 0x8a, 0x95, 0x1a, 0x74, 0xfd, 0x28, 0xdf, 0xc1, 0x84, 0xc7, 0x2a, 0x65, 0xea, 0xc9, + 0x51, 0xac, 0x9f, 0x44, 0xc8, 0x3b, 0x7c, 0x53, 0x21, 0x81, 0x63, 0x04, 0xd1, 0xf7, 0x68, 0x30, + 0xe5, 0xef, 0xfa, 0x01, 0x69, 0x85, 0x7d, 0x38, 0x75, 0xd4, 0x7d, 0x60, 0x36, 0xe9, 0x7a, 0x8c, + 0x08, 0x4e, 0x10, 0x65, 0x31, 0x35, 0x5a, 0x46, 0x93, 0x5c, 0xaf, 0xdc, 0xb0, 0x9a, 0x5b, 0x61, + 0xd0, 0x85, 0x35, 0xe2, 0x35, 0x88, 0x13, 0x30, 0xc5, 0x66, 0x48, 0xc4, 0xd4, 0xc8, 0xaf, 0x86, + 0xbb, 0xe1, 0x40, 0xaf, 0xc1, 0x9c, 0x00, 0x2f, 0xbb, 0xf7, 0x52, 0x14, 0x66, 0x18, 0x05, 0xe6, + 0x05, 0x58, 0xcb, 0xad, 0x85, 0xbb, 0x60, 0x40, 0x35, 0x38, 0xed, 0x13, 0x8f, 0x5d, 0x29, 0xf1, + 0x88, 0x4a, 0x6b, 0x1d, 0xdb, 0xf6, 0x99, 0x6a, 0x21, 0x5e, 0x40, 0xd4, 0xd3, 0x60, 0x9c, 0xd5, + 0x06, 0xbd, 0x10, 0x3e, 0xb2, 0xdc, 0xa5, 0x05, 0x1f, 0x5a, 0xab, 0xcf, 0x9e, 0x66, 0xfd, 0x3b, + 0xad, 0xbc, 0x9d, 0x94, 0x20, 0x9c, 0xac, 0x4b, 0x4f, 0x73, 0x59, 0xb4, 0xd8, 0xf1, 0xfc, 0x60, + 0xf6, 0x0c, 0x6b, 0xcc, 0x4e, 0x73, 0xac, 0x02, 0x70, 0xbc, 0x1e, 0xba, 0x0a, 0x53, 0x3e, 0x69, + 0x34, 0xdc, 0x56, 0x5b, 0xe8, 0xa9, 0xb3, 0x67, 0x59, 0xef, 0xf9, 0x0a, 0xc6, 0x20, 0x38, 0x51, + 0x13, 0xed, 0xc2, 0xe9, 0x30, 0x36, 0xe4, 0xb2, 0xdb, 0x5c, 0x31, 0x76, 0x98, 0x70, 0x7c, 0xee, + 0x60, 0xfe, 0x38, 0x2f, 0x3d, 0x28, 0xe6, 0x3f, 0xd4, 0x31, 0x9c, 0xc0, 0x0a, 0x76, 0xf9, 0x74, + 0x55, 0xd2, 0xe8, 0x70, 0x16, 0x0d, 0xb4, 0x0c, 0x67, 0x12, 0xc5, 0xd7, 0x2c, 0x9b, 0xf8, 0xb3, + 0xe7, 0xd9, 0xb0, 0x99, 0xb1, 0xa9, 0x92, 0x01, 0xc7, 0x99, 0xad, 0xd0, 0x2d, 0x38, 0xdb, 0xf6, + 0xdc, 0x80, 0x34, 0x82, 0x9b, 0x54, 0x20, 0xb0, 0xc5, 0x00, 0xfd, 0xd9, 0x59, 0x36, 0x17, 0xec, + 0x3a, 0x6d, 0x2d, 0xab, 0x02, 0xce, 0x6e, 0x87, 0x3e, 0xab, 0xc1, 0x45, 0x3f, 0xf0, 0x88, 0xd1, + 0xb2, 0x9c, 0x66, 0xc5, 0x75, 0x1c, 0xc2, 0x18, 0x53, 0xcd, 0x8c, 0x1e, 0x10, 0x3d, 0x54, 0xe8, + 0x14, 0xd1, 0xf7, 0xf7, 0xca, 0x17, 0xeb, 0x5d, 0x31, 0xe3, 0x03, 0x28, 0xa3, 0x37, 0x01, 0x5a, + 0xa4, 0xe5, 0x7a, 0xbb, 0x94, 0x23, 0xcd, 0xce, 0x15, 0xd7, 0x83, 0x57, 0x42, 0x2c, 0xfc, 0xf3, + 0x8f, 0x5d, 0x04, 0x46, 0x40, 0xac, 0x90, 0xd3, 0xf7, 0x4a, 0x70, 0x36, 0x93, 0xd5, 0xd3, 0x2f, + 0x80, 0xd7, 0x5b, 0x90, 0x59, 0x3c, 0xc4, 0xdd, 0x19, 0xfb, 0x02, 0x56, 0xe2, 0x20, 0x9c, 0xac, + 0x4b, 0x05, 0x31, 0xf6, 0xa5, 0x5e, 0xab, 0x47, 0xed, 0x4b, 0x91, 0x20, 0x56, 0x4b, 0xc0, 0x70, + 0xaa, 0x36, 0xaa, 0xc0, 0x8c, 0x28, 0xab, 0x51, 0x5d, 0xc6, 0xbf, 0xe6, 0x11, 0x29, 0xe2, 0x52, + 0xad, 0x60, 0xa6, 0x96, 0x04, 0xe2, 0x74, 0x7d, 0x3a, 0x0a, 0xfa, 0x43, 0xed, 0xc5, 0x60, 0x34, + 0x8a, 0xd5, 0x38, 0x08, 0x27, 0xeb, 0x4a, 0x65, 0x33, 0xd6, 0x85, 0xa1, 0x68, 0x14, 0xab, 0x09, + 0x18, 0x4e, 0xd5, 0xd6, 0xff, 0xe3, 0x20, 0x3c, 0xda, 0x83, 0x78, 0x84, 0x5a, 0xd9, 0xd3, 0x7d, + 0xf8, 0x0f, 0xb7, 0xb7, 0xe5, 0x69, 0xe7, 0x2c, 0xcf, 0xe1, 0xe9, 0xf5, 0xba, 0x9c, 0x7e, 0xde, + 0x72, 0x1e, 0x9e, 0x64, 0xef, 0xcb, 0xdf, 0xca, 0x5e, 0xfe, 0x82, 0xb3, 0x7a, 0xe0, 0x76, 0x69, + 0xe7, 0x6c, 0x97, 0x82, 0xb3, 0xda, 0xc3, 0xf6, 0xfa, 0xbd, 0x41, 0x78, 0xac, 0x17, 0x51, 0xad, + 0xe0, 0xfe, 0xca, 0x60, 0x79, 0xc7, 0xba, 0xbf, 0xf2, 0xde, 0x68, 0x1e, 0xe3, 0xfe, 0xca, 0x20, + 0x79, 0xdc, 0xfb, 0x2b, 0x6f, 0x56, 0x8f, 0x6b, 0x7f, 0xe5, 0xcd, 0x6a, 0x0f, 0xfb, 0xeb, 0x4f, + 0x92, 0xe7, 0x43, 0x28, 0x2f, 0xd6, 0x60, 0xa0, 0xd1, 0xee, 0x14, 0x64, 0x52, 0xcc, 0xd3, 0xaa, + 0xb2, 0x76, 0x1b, 0x53, 0x1c, 0x08, 0xc3, 0x30, 0xdf, 0x3f, 0x05, 0x59, 0x10, 0xf3, 0x9e, 0xe3, + 0x5b, 0x12, 0x0b, 0x4c, 0x74, 0xaa, 0x48, 0x7b, 0x8b, 0xb4, 0x88, 0x67, 0xd8, 0xf5, 0xc0, 0xf5, + 0x8c, 0x66, 0x51, 0x6e, 0xc3, 0xcd, 0xf0, 0x09, 0x5c, 0x38, 0x85, 0x9d, 0x4e, 0x48, 0xdb, 0x32, + 0x0b, 0xf2, 0x17, 0x36, 0x21, 0x6b, 0xb5, 0x2a, 0xa6, 0x38, 0xf4, 0x2f, 0x8f, 0x82, 0x12, 0xae, + 0x18, 0x7d, 0x4a, 0x83, 0x99, 0x46, 0x32, 0xde, 0x5b, 0x3f, 0x4e, 0x35, 0xa9, 0xe0, 0x71, 0x7c, + 0xcb, 0xa7, 0x8a, 0x71, 0x9a, 0x2c, 0xfa, 0x2e, 0x8d, 0x5b, 0xaa, 0xc2, 0x2b, 0x21, 0x31, 0xad, + 0xd7, 0x8f, 0xe8, 0xf2, 0x34, 0x32, 0x79, 0x45, 0xf7, 0x74, 0x71, 0x82, 0xe8, 0xf3, 0x1a, 0x9c, + 0xbd, 0x9b, 0x65, 0x60, 0x17, 0x93, 0x7f, 0xab, 0x68, 0x57, 0x72, 0x2c, 0xf6, 0x5c, 0xe2, 0xcc, + 0xac, 0x80, 0xb3, 0x3b, 0x12, 0xce, 0x52, 0x68, 0x73, 0x14, 0xdf, 0x69, 0xe1, 0x59, 0x4a, 0x18, + 0x2f, 0xa3, 0x59, 0x0a, 0x01, 0x38, 0x4e, 0x10, 0xb5, 0x61, 0xec, 0xae, 0x34, 0xf4, 0x0a, 0xe3, + 0x4e, 0xa5, 0x28, 0x75, 0xc5, 0x5a, 0xcc, 0x9d, 0x86, 0xc2, 0x42, 0x1c, 0x11, 0x41, 0x5b, 0x30, + 0x72, 0x97, 0xf3, 0x0a, 0x61, 0x94, 0x59, 0xe8, 0x5b, 0x85, 0xe5, 0xb6, 0x01, 0x51, 0x84, 0x25, + 0x7a, 0xd5, 0x9f, 0x7a, 0xf4, 0x80, 0x17, 0x39, 0x9f, 0xd5, 0xe0, 0xec, 0x36, 0xf1, 0x02, 0xab, + 0x91, 0xbc, 0xde, 0x18, 0x2b, 0xae, 0x66, 0xbf, 0x9c, 0x85, 0x90, 0x6f, 0x93, 0x4c, 0x10, 0xce, + 0xee, 0x02, 0x55, 0xba, 0xb9, 0x95, 0xba, 0x1e, 0x18, 0x81, 0xd5, 0x58, 0x77, 0xef, 0x12, 0x27, + 0x4a, 0x45, 0xc8, 0xcc, 0x23, 0x22, 0x90, 0xe5, 0x52, 0x7e, 0x35, 0xdc, 0x0d, 0x87, 0xfe, 0x87, + 0x1a, 0xa4, 0x6c, 0xad, 0xe8, 0x87, 0x34, 0x98, 0xd8, 0x24, 0x46, 0xd0, 0xf1, 0xc8, 0x75, 0x23, + 0x08, 0x03, 0x5c, 0xbc, 0x7c, 0x14, 0x26, 0xde, 0xf9, 0x6b, 0x0a, 0x62, 0xee, 0xfc, 0x10, 0x46, + 0x23, 0x57, 0x41, 0x38, 0xd6, 0x83, 0xb9, 0x97, 0x60, 0x26, 0xd5, 0xf0, 0x50, 0xd7, 0x6e, 0xff, + 0x42, 0x83, 0xac, 0x64, 0xa5, 0xe8, 0x35, 0x18, 0x32, 0x4c, 0x33, 0xcc, 0xf3, 0xf5, 0x5c, 0x31, + 0x3f, 0x1c, 0x53, 0x8d, 0x23, 0xc2, 0x7e, 0x62, 0x8e, 0x16, 0x5d, 0x03, 0x64, 0xc4, 0xee, 0x39, + 0x57, 0xa2, 0xd7, 0xf1, 0xec, 0x7a, 0x68, 0x21, 0x05, 0xc5, 0x19, 0x2d, 0xf4, 0x4f, 0x68, 0x80, + 0xd2, 0xf1, 0xeb, 0x91, 0x07, 0xa3, 0xdb, 0xf1, 0xe0, 0xd9, 0xd5, 0xa3, 0x08, 0x9e, 0x1d, 0x39, + 0x75, 0x85, 0xc1, 0xa8, 0x43, 0x3a, 0xfa, 0x9f, 0x6b, 0x10, 0xe5, 0x02, 0x42, 0xef, 0x85, 0x71, + 0x93, 0xf8, 0x0d, 0xcf, 0x6a, 0x07, 0xd1, 0x13, 0xb8, 0xf0, 0x7d, 0x4e, 0x35, 0x02, 0x61, 0xb5, + 0x1e, 0xd2, 0x61, 0x38, 0x30, 0xfc, 0xbb, 0xb5, 0xaa, 0xd0, 0xfb, 0xd8, 0x29, 0xbd, 0xce, 0x4a, + 0xb0, 0x80, 0x44, 0x11, 0x0a, 0x07, 0x7a, 0x88, 0x50, 0x88, 0x36, 0x8f, 0x20, 0x1c, 0x23, 0x3a, + 0x38, 0x14, 0xa3, 0xfe, 0xd3, 0x25, 0x38, 0x45, 0xab, 0xac, 0x18, 0x96, 0x13, 0x10, 0x87, 0xbd, + 0x22, 0x29, 0x38, 0x09, 0x4d, 0x98, 0x0c, 0x62, 0x2f, 0x51, 0x0f, 0xff, 0x0c, 0x33, 0xf4, 0x1c, + 0x8a, 0xbf, 0x3f, 0x8d, 0xe3, 0x45, 0xcf, 0xc9, 0x67, 0x3c, 0x5c, 0x43, 0x7e, 0x54, 0x6e, 0x55, + 0xf9, 0xb8, 0x10, 0xc5, 0xf2, 0x49, 0xc5, 0x5e, 0xec, 0x3c, 0x0b, 0x93, 0xc2, 0x61, 0x9c, 0x87, + 0x9a, 0x14, 0x1a, 0x32, 0x3b, 0x61, 0xae, 0xa9, 0x00, 0x1c, 0xaf, 0xa7, 0xff, 0x56, 0x09, 0xe2, + 0x69, 0xaa, 0x8a, 0xce, 0x52, 0x3a, 0xce, 0x66, 0xe9, 0xd8, 0xe2, 0x6c, 0xbe, 0x9b, 0xe5, 0x78, + 0xe4, 0x29, 0x8a, 0xf9, 0xbd, 0xb1, 0x9a, 0x99, 0x91, 0x27, 0x18, 0x0e, 0x6b, 0x44, 0xd3, 0x3a, + 0x78, 0xe8, 0x69, 0x7d, 0xaf, 0xf0, 0x24, 0x1d, 0x8a, 0x45, 0x3b, 0x95, 0x9e, 0xa4, 0x33, 0xb1, + 0x86, 0xca, 0xa3, 0xa3, 0x2f, 0x6a, 0x30, 0x15, 0x7f, 0xb8, 0x8a, 0xee, 0xa4, 0x1e, 0xd9, 0xf2, + 0x89, 0xbd, 0x2c, 0x87, 0x5c, 0xf4, 0xa1, 0xed, 0x1d, 0x18, 0xf3, 0xc3, 0xdc, 0x5a, 0x87, 0x9f, + 0x72, 0x26, 0x09, 0x44, 0x29, 0xb5, 0x22, 0x5c, 0xfa, 0x2a, 0xbc, 0x73, 0xd9, 0x35, 0xcc, 0x45, + 0xc3, 0xa6, 0x1f, 0x8f, 0x27, 0x1c, 0xcd, 0x7c, 0x26, 0x26, 0xac, 0x79, 0x6e, 0xe0, 0x36, 0x5c, + 0x9b, 0x1e, 0xe2, 0x86, 0x6d, 0xbb, 0xf7, 0xd2, 0xb9, 0xaf, 0x17, 0x78, 0x31, 0x96, 0x70, 0xfd, + 0xcb, 0x1a, 0x8c, 0x88, 0x00, 0xfa, 0x3d, 0xbc, 0xf4, 0xdb, 0x84, 0x21, 0xa6, 0xaa, 0xf5, 0x23, + 0x22, 0xd7, 0xb7, 0x5c, 0x37, 0x88, 0xe5, 0xf3, 0x60, 0x8f, 0x47, 0x78, 0xae, 0x2e, 0x8e, 0x9e, + 0x79, 0x58, 0x7a, 0x8d, 0x2d, 0x2b, 0x20, 0xcc, 0x91, 0x44, 0x7c, 0x7a, 0xdc, 0xc3, 0x52, 0x29, + 0xc7, 0xb1, 0x5a, 0xfa, 0xe7, 0x06, 0xe1, 0x92, 0x40, 0x9c, 0x92, 0x1b, 0x43, 0xae, 0xbf, 0x0b, + 0xa7, 0xc5, 0xec, 0x57, 0x3d, 0xc3, 0x0a, 0x9d, 0x14, 0x8a, 0xa9, 0xec, 0x22, 0x97, 0x7c, 0x0a, + 0x1d, 0xce, 0xa2, 0xc1, 0xc3, 0x0c, 0xb3, 0xe2, 0x1b, 0xc4, 0xb0, 0x83, 0x2d, 0x49, 0xbb, 0xd4, + 0x4f, 0x98, 0xe1, 0x34, 0x3e, 0x9c, 0x49, 0x85, 0x39, 0x49, 0x08, 0x40, 0xc5, 0x23, 0x86, 0xea, + 0xa1, 0xd1, 0xc7, 0xfb, 0x8f, 0x95, 0x4c, 0x8c, 0x38, 0x87, 0x12, 0xb3, 0x7d, 0x1a, 0x3b, 0xcc, + 0x94, 0x82, 0x49, 0xe0, 0x59, 0x2c, 0x2f, 0x4b, 0x68, 0xfd, 0x5f, 0x89, 0x83, 0x70, 0xb2, 0x2e, + 0xba, 0x0a, 0x53, 0xcc, 0xe9, 0x24, 0x0a, 0x37, 0x38, 0x14, 0x45, 0xb4, 0x59, 0x8d, 0x41, 0x70, + 0xa2, 0xa6, 0xfe, 0xb1, 0x12, 0x4c, 0x1c, 0x32, 0xef, 0x5a, 0x47, 0x91, 0x10, 0xfa, 0x78, 0x74, + 0x95, 0x91, 0xa0, 0xa2, 0x9b, 0x90, 0x80, 0x5e, 0x81, 0xa9, 0x0e, 0x63, 0xab, 0x32, 0x64, 0x92, + 0xd8, 0xff, 0xdf, 0x48, 0x47, 0x79, 0x3b, 0x06, 0x79, 0xb0, 0x57, 0x9e, 0x53, 0xd1, 0xc7, 0xa1, + 0x38, 0x81, 0x47, 0xff, 0xf4, 0x00, 0x9c, 0xce, 0xe8, 0x0d, 0x73, 0x4e, 0x20, 0x09, 0x39, 0xa6, + 0x1f, 0xe7, 0x84, 0x94, 0x4c, 0x14, 0x3a, 0x27, 0x24, 0x21, 0x38, 0x45, 0x17, 0xbd, 0x0c, 0x03, + 0x0d, 0xcf, 0x12, 0x13, 0xfe, 0x6c, 0x21, 0x2d, 0x1c, 0xd7, 0x16, 0xc7, 0x05, 0xc5, 0x81, 0x0a, + 0xae, 0x61, 0x8a, 0x90, 0x9e, 0xc6, 0x2a, 0xbb, 0x90, 0xa2, 0x11, 0x3b, 0x8d, 0x55, 0xae, 0xe2, + 0xe3, 0x78, 0x3d, 0xf4, 0x0a, 0xcc, 0x0a, 0xf5, 0x48, 0x32, 0x7f, 0xd7, 0xf1, 0x03, 0xfa, 0x65, + 0x07, 0xe2, 0xf4, 0x62, 0x7e, 0x7b, 0x37, 0x73, 0xea, 0xe0, 0xdc, 0xd6, 0xfa, 0x3f, 0xd7, 0xe0, + 0xa1, 0xdc, 0x0c, 0x27, 0x3d, 0x6c, 0xd0, 0x9d, 0xd4, 0x06, 0x3d, 0xca, 0xfc, 0x2f, 0xdd, 0x04, + 0xd9, 0x3f, 0x1e, 0x00, 0x35, 0xd1, 0x21, 0x5a, 0xe9, 0xc7, 0x68, 0x15, 0xad, 0x95, 0x34, 0x5c, + 0xad, 0xc0, 0x40, 0xb3, 0xdd, 0x29, 0x68, 0xb5, 0x0a, 0xd1, 0x5d, 0xa7, 0xe8, 0x9a, 0xed, 0x0e, + 0x7a, 0x39, 0xb4, 0x83, 0x15, 0xb3, 0x54, 0x85, 0x8f, 0xb1, 0x12, 0xb6, 0x30, 0xb9, 0x42, 0x83, + 0xb9, 0x2b, 0xd4, 0x82, 0x11, 0x5f, 0x18, 0xc9, 0x86, 0x8a, 0xc7, 0x34, 0x53, 0x66, 0x5a, 0x18, + 0xc5, 0xb8, 0xfa, 0x2e, 0x6d, 0x66, 0x92, 0x06, 0x55, 0x0d, 0x3a, 0xec, 0x01, 0x3c, 0xb3, 0x4b, + 0x8c, 0x72, 0xd5, 0xe0, 0x36, 0x2b, 0xc1, 0x02, 0x92, 0x3a, 0x5c, 0x47, 0x7a, 0x3a, 0x5c, 0xbf, + 0xaf, 0x04, 0x28, 0xdd, 0x0d, 0xf4, 0x28, 0x0c, 0x31, 0xd1, 0x47, 0x6c, 0xd2, 0x50, 0x91, 0x63, + 0xf2, 0x11, 0xe6, 0x30, 0x54, 0x17, 0x11, 0x9a, 0x8a, 0x2d, 0x27, 0xf3, 0x4b, 0x12, 0xf4, 0x94, + 0x70, 0x4e, 0x97, 0x62, 0xef, 0x89, 0xb2, 0xa4, 0x95, 0xdb, 0x30, 0xd2, 0xb2, 0x1c, 0x76, 0x55, + 0x5b, 0xcc, 0x76, 0xc8, 0xdd, 0x27, 0x38, 0x0a, 0x2c, 0x71, 0xe9, 0xbf, 0x57, 0xa2, 0x5b, 0x3f, + 0x52, 0x60, 0x76, 0x01, 0x8c, 0x4e, 0xe0, 0x72, 0xd6, 0x2b, 0xbe, 0x80, 0x5a, 0xb1, 0x55, 0x0e, + 0x91, 0x2e, 0x84, 0x08, 0xf9, 0x25, 0x63, 0xf4, 0x1b, 0x2b, 0xc4, 0x28, 0xe9, 0xc0, 0x6a, 0x91, + 0x3b, 0x96, 0x63, 0xba, 0xf7, 0xc4, 0xf4, 0xf6, 0x4b, 0x7a, 0x3d, 0x44, 0xc8, 0x49, 0x47, 0xbf, + 0xb1, 0x42, 0x8c, 0x32, 0x45, 0x66, 0x07, 0x71, 0x58, 0x4a, 0x3a, 0xd1, 0x37, 0xd7, 0xb6, 0xa5, + 0x3c, 0x31, 0xca, 0x99, 0x62, 0x25, 0xa7, 0x0e, 0xce, 0x6d, 0xad, 0xff, 0x9c, 0x06, 0x67, 0x33, + 0xa7, 0x02, 0x5d, 0x87, 0x99, 0x54, 0xda, 0x29, 0x21, 0xe1, 0x86, 0x79, 0x1d, 0x53, 0xb9, 0xaa, + 0x70, 0xba, 0x0d, 0xaa, 0x85, 0x42, 0xa0, 0xca, 0x76, 0x85, 0x1f, 0x9c, 0x2a, 0xd4, 0xa9, 0x60, + 0x9c, 0xd5, 0x46, 0xff, 0xd6, 0x58, 0x67, 0xa3, 0xc9, 0xa2, 0x5f, 0xc6, 0x06, 0x69, 0x86, 0xef, + 0x39, 0xc3, 0x2f, 0x63, 0x91, 0x16, 0x62, 0x0e, 0x43, 0x8f, 0xa8, 0xaf, 0xa4, 0x43, 0xbe, 0x25, + 0x5f, 0x4a, 0xeb, 0xdf, 0x01, 0xe7, 0x73, 0xee, 0x9e, 0x51, 0x15, 0x26, 0xfc, 0x7b, 0x46, 0x7b, + 0x91, 0x6c, 0x19, 0xdb, 0x96, 0x88, 0x49, 0xc2, 0x5d, 0x14, 0x27, 0xea, 0x4a, 0xf9, 0x83, 0xc4, + 0x6f, 0x1c, 0x6b, 0xa5, 0x07, 0x00, 0xc2, 0x95, 0xd5, 0x72, 0x9a, 0x68, 0x13, 0x46, 0x0d, 0x9b, + 0x78, 0x41, 0x14, 0x81, 0xf1, 0x9b, 0x0b, 0xd9, 0x74, 0x04, 0x0e, 0xfe, 0x74, 0x42, 0xfe, 0xc2, + 0x21, 0x6e, 0xfd, 0x1f, 0x68, 0x70, 0x2e, 0x3b, 0x0a, 0x45, 0x0f, 0x67, 0x5e, 0x0b, 0xc6, 0xbd, + 0xa8, 0x99, 0xd8, 0xf4, 0xef, 0x53, 0x63, 0x5d, 0x2b, 0xc1, 0x1d, 0xa9, 0xc0, 0x5a, 0xf1, 0x5c, + 0x5f, 0xae, 0x7c, 0x32, 0xfc, 0x75, 0xa8, 0x41, 0x2b, 0x3d, 0xc1, 0x2a, 0x7e, 0x16, 0x8a, 0x9e, + 0x52, 0xf7, 0xdb, 0x46, 0x83, 0x98, 0x27, 0x9c, 0x0c, 0xf4, 0x08, 0xe2, 0x3f, 0x67, 0xf7, 0xfd, + 0x78, 0x43, 0xd1, 0xe7, 0xd0, 0x3c, 0x38, 0x14, 0x7d, 0x76, 0xc3, 0xb7, 0x49, 0x8c, 0xe4, 0xec, + 0xce, 0xe7, 0x3c, 0xba, 0xfc, 0xf4, 0x70, 0xde, 0x68, 0x0f, 0x99, 0xe1, 0x73, 0xfb, 0x18, 0x33, + 0x7c, 0x4e, 0xfd, 0x75, 0x76, 0xcf, 0x8c, 0xec, 0x9e, 0x89, 0x8c, 0x93, 0xc3, 0x27, 0x94, 0x71, + 0xf2, 0x0d, 0x18, 0x6e, 0x1b, 0x1e, 0x71, 0xe4, 0x15, 0x50, 0xad, 0xdf, 0x74, 0xb6, 0x11, 0x17, + 0x0c, 0x3f, 0xc9, 0x35, 0x46, 0x00, 0x0b, 0x42, 0x19, 0x0f, 0xf7, 0x47, 0x8f, 0xeb, 0xe1, 0xfe, + 0x9f, 0x6a, 0x70, 0xa1, 0x1b, 0xdb, 0x60, 0x2a, 0x6a, 0x23, 0xf1, 0x99, 0xf4, 0xa3, 0xa2, 0xa6, + 0xb8, 0x61, 0xa8, 0xa2, 0x26, 0x21, 0x38, 0x45, 0x37, 0x27, 0x73, 0x7f, 0xa9, 0x48, 0xe6, 0x7e, + 0xfd, 0x97, 0x4a, 0x00, 0xab, 0x24, 0xb8, 0xe7, 0x7a, 0x77, 0xe9, 0x19, 0x7c, 0x21, 0x66, 0x84, + 0x1b, 0xfd, 0xda, 0x85, 0xda, 0xba, 0x00, 0x83, 0x6d, 0xd7, 0xf4, 0x85, 0x7c, 0xcd, 0x3a, 0xc2, + 0xdc, 0x88, 0x59, 0x29, 0x2a, 0xc3, 0x10, 0xf3, 0x65, 0x10, 0xaa, 0x0f, 0x33, 0xe1, 0xad, 0xd2, + 0x02, 0xcc, 0xcb, 0x29, 0x07, 0x13, 0xef, 0x5d, 0x7d, 0x61, 0xa8, 0x9d, 0xe0, 0xa1, 0x48, 0x79, + 0x19, 0x0e, 0xa1, 0xe8, 0x2a, 0x80, 0xd5, 0xbe, 0x66, 0xb4, 0x2c, 0xdb, 0x12, 0x9f, 0xd3, 0x18, + 0xb3, 0x2d, 0x41, 0x6d, 0x4d, 0x96, 0x3e, 0xd8, 0x2b, 0x8f, 0x8a, 0x5f, 0xbb, 0x58, 0xa9, 0xad, + 0x7f, 0x41, 0x83, 0xe9, 0x68, 0xf2, 0xc4, 0x56, 0x91, 0x3d, 0xe7, 0xa1, 0x20, 0x73, 0x7b, 0xce, + 0xa3, 0xff, 0x76, 0xef, 0x39, 0x37, 0x11, 0xe4, 0xf5, 0xfc, 0x69, 0x18, 0x27, 0x3c, 0x1c, 0x46, + 0xad, 0x8a, 0x39, 0x0f, 0x1a, 0xe3, 0xea, 0xca, 0x52, 0x54, 0x8c, 0xd5, 0x3a, 0xfa, 0x5f, 0x0c, + 0xc0, 0xc4, 0x6a, 0xd3, 0x72, 0x76, 0x64, 0xdc, 0x8f, 0xf0, 0x12, 0x4d, 0x3b, 0x9e, 0x4b, 0xb4, + 0x57, 0x60, 0xd6, 0x56, 0x0d, 0xc6, 0x5c, 0xb0, 0x31, 0x9c, 0x66, 0x38, 0x03, 0x4c, 0x4e, 0x5f, + 0xce, 0xa9, 0x83, 0x73, 0x5b, 0xa3, 0x00, 0x86, 0x1b, 0x32, 0xeb, 0x51, 0xe1, 0x58, 0x16, 0xea, + 0x5c, 0xcc, 0xab, 0xcf, 0xba, 0x43, 0x9e, 0x24, 0xb6, 0xa7, 0xa0, 0x85, 0x3e, 0xae, 0xc1, 0x59, + 0xb2, 0xc3, 0xc3, 0x1a, 0xac, 0x7b, 0xc6, 0xe6, 0xa6, 0xd5, 0x10, 0xaf, 0x51, 0xf8, 0x4e, 0x5c, + 0xde, 0xdf, 0x2b, 0x9f, 0x5d, 0xca, 0xaa, 0xf0, 0x60, 0xaf, 0x7c, 0x39, 0x33, 0xca, 0x04, 0x5b, + 0xcd, 0xcc, 0x26, 0x38, 0x9b, 0xd4, 0xdc, 0x73, 0x30, 0x7e, 0x88, 0x37, 0x8c, 0xb1, 0x58, 0x12, + 0xbf, 0x5c, 0x82, 0x09, 0xba, 0xdd, 0x96, 0xdd, 0x86, 0x61, 0x57, 0x57, 0xeb, 0xe8, 0xc9, 0x64, + 0x04, 0xa8, 0xd0, 0x58, 0x9f, 0x8a, 0x02, 0xb5, 0x0c, 0x67, 0x36, 0x5d, 0xaf, 0x41, 0xd6, 0x2b, + 0x6b, 0xeb, 0xae, 0xf0, 0x29, 0xa9, 0xae, 0xd6, 0x85, 0xde, 0xc2, 0x0c, 0xc2, 0xd7, 0x32, 0xe0, + 0x38, 0xb3, 0x15, 0xba, 0x05, 0x67, 0xa3, 0xf2, 0xdb, 0x6d, 0xee, 0x4c, 0x4b, 0xd1, 0x0d, 0x44, + 0xce, 0xc0, 0xd7, 0xb2, 0x2a, 0xe0, 0xec, 0x76, 0xc8, 0x80, 0x87, 0x45, 0xf8, 0xbd, 0x6b, 0xae, + 0x77, 0xcf, 0xf0, 0xcc, 0x38, 0xda, 0xc1, 0xe8, 0xce, 0xbd, 0x9a, 0x5f, 0x0d, 0x77, 0xc3, 0xa1, + 0xbf, 0xa5, 0x41, 0x3c, 0xbe, 0x16, 0x7a, 0x08, 0x06, 0x3c, 0x91, 0xa8, 0x47, 0xc4, 0x99, 0xa2, + 0x22, 0x3c, 0x2d, 0x43, 0xf3, 0x00, 0x5e, 0x14, 0xe4, 0xab, 0x14, 0x45, 0xc7, 0x56, 0xc2, 0x73, + 0x29, 0x35, 0x28, 0xaa, 0xc0, 0x68, 0x0a, 0x86, 0xc7, 0x50, 0xad, 0x1b, 0x4d, 0x4c, 0xcb, 0x58, + 0x18, 0x74, 0xab, 0x49, 0x7c, 0x69, 0xf0, 0xe3, 0x61, 0xd0, 0x59, 0x09, 0x16, 0x10, 0xfd, 0xc7, + 0x86, 0x41, 0x89, 0x8b, 0x70, 0x08, 0x11, 0xee, 0xa7, 0x34, 0x38, 0xd3, 0xb0, 0x2d, 0xe2, 0x04, + 0x89, 0x27, 0xc6, 0x9c, 0xb7, 0xdf, 0x2e, 0x14, 0xb0, 0xa1, 0x4d, 0x9c, 0x5a, 0x55, 0xf8, 0x45, + 0x57, 0x32, 0x90, 0x0b, 0xdf, 0xf1, 0x0c, 0x08, 0xce, 0xec, 0x0c, 0x1b, 0x0f, 0x2b, 0xaf, 0x55, + 0xd5, 0xa8, 0x5d, 0x15, 0x51, 0x86, 0x43, 0x28, 0x65, 0x8b, 0x4d, 0xcf, 0xed, 0xb4, 0xfd, 0x0a, + 0x7b, 0xfe, 0xc4, 0x67, 0x8c, 0xb1, 0xc5, 0xeb, 0x51, 0x31, 0x56, 0xeb, 0xa0, 0x67, 0x60, 0x82, + 0xff, 0x5c, 0xf3, 0xc8, 0xa6, 0xb5, 0x23, 0x4e, 0x0c, 0x66, 0x93, 0xba, 0xae, 0x94, 0xe3, 0x58, + 0x2d, 0x16, 0x78, 0xc7, 0xf7, 0x3b, 0xc4, 0xbb, 0x8d, 0x97, 0x45, 0xce, 0x3e, 0x1e, 0x78, 0x47, + 0x16, 0xe2, 0x08, 0x8e, 0x7e, 0x44, 0x83, 0x29, 0x8f, 0xbc, 0xd1, 0xb1, 0x3c, 0x2a, 0x5f, 0x18, + 0x56, 0xcb, 0x17, 0xc1, 0x29, 0x70, 0x7f, 0x01, 0x31, 0xe6, 0x71, 0x0c, 0x29, 0xe7, 0x5e, 0xe1, + 0x9d, 0x69, 0x1c, 0x88, 0x13, 0x3d, 0xa0, 0x53, 0xe5, 0x5b, 0x4d, 0xc7, 0x72, 0x9a, 0x0b, 0x76, + 0xd3, 0x9f, 0x1d, 0x8d, 0x4e, 0x90, 0x7a, 0x54, 0x8c, 0xd5, 0x3a, 0xe8, 0x59, 0x98, 0xec, 0xf8, + 0x94, 0x27, 0xb5, 0x08, 0x9f, 0xdf, 0xb1, 0xe8, 0x52, 0xf9, 0xb6, 0x0a, 0xc0, 0xf1, 0x7a, 0xe8, + 0x2a, 0x4c, 0xc9, 0x02, 0x31, 0xcb, 0xc0, 0x23, 0xa6, 0xb3, 0x6b, 0x85, 0x18, 0x04, 0x27, 0x6a, + 0xce, 0x2d, 0xc0, 0xe9, 0x8c, 0x61, 0x1e, 0x8a, 0xf1, 0xfd, 0xa5, 0x06, 0x67, 0xb9, 0x48, 0x24, + 0xb3, 0xfd, 0xc9, 0xc8, 0xe0, 0xd9, 0x41, 0xb6, 0xb5, 0x63, 0x0d, 0xb2, 0xfd, 0x35, 0x08, 0x26, + 0xae, 0xff, 0x6c, 0x09, 0xde, 0x79, 0xe0, 0x77, 0x89, 0x7e, 0x5c, 0x83, 0x71, 0xb2, 0x13, 0x78, + 0x46, 0xf8, 0x46, 0x94, 0x6e, 0xd2, 0xcd, 0x63, 0x61, 0x02, 0xf3, 0x4b, 0x11, 0x21, 0xbe, 0x71, + 0x43, 0x3d, 0x44, 0x81, 0x60, 0xb5, 0x3f, 0x94, 0x15, 0xf2, 0x8c, 0x02, 0xaa, 0xf7, 0x09, 0x0f, + 0x30, 0x84, 0x05, 0x64, 0xee, 0x45, 0x98, 0x4e, 0x62, 0x3e, 0xd4, 0x5e, 0xf9, 0xc5, 0x12, 0x8c, + 0xac, 0x79, 0xee, 0xeb, 0xa4, 0x71, 0x12, 0xf1, 0xbb, 0x8c, 0x98, 0x95, 0xa5, 0x90, 0x0e, 0x29, + 0x3a, 0x9b, 0x6b, 0x56, 0xb1, 0x12, 0x66, 0x95, 0x85, 0x7e, 0x88, 0x74, 0xb7, 0xa3, 0xfc, 0xba, + 0x06, 0xe3, 0xa2, 0xe6, 0x09, 0x18, 0x4e, 0xbe, 0x33, 0x6e, 0x38, 0x79, 0xbe, 0x8f, 0x71, 0xe5, + 0x58, 0x4a, 0x3e, 0xab, 0xc1, 0xa4, 0xa8, 0xb1, 0x42, 0x5a, 0x1b, 0xc4, 0x43, 0xd7, 0x60, 0xc4, + 0xef, 0xb0, 0x85, 0x14, 0x03, 0x7a, 0x58, 0xb5, 0xfe, 0x79, 0x1b, 0x46, 0x83, 0x76, 0xbf, 0xce, + 0xab, 0x28, 0x79, 0xf3, 0x78, 0x01, 0x96, 0x8d, 0xd1, 0x25, 0x18, 0xf4, 0x5c, 0x3b, 0x15, 0xd5, + 0x15, 0xbb, 0x36, 0xc1, 0x0c, 0x42, 0x75, 0x05, 0xfa, 0x57, 0xea, 0x01, 0x4c, 0x57, 0xa0, 0x60, + 0x1f, 0xf3, 0x72, 0xfd, 0x0b, 0x43, 0xe1, 0x64, 0x33, 0xc5, 0xf0, 0x06, 0x8c, 0x35, 0x3c, 0x62, + 0x04, 0xc4, 0x5c, 0xdc, 0xed, 0xa5, 0x73, 0xec, 0xb8, 0xaa, 0xc8, 0x16, 0x38, 0x6a, 0x4c, 0x4f, + 0x06, 0xd5, 0xe1, 0xa7, 0x14, 0x1d, 0xa2, 0xb9, 0xce, 0x3e, 0xdf, 0x0c, 0x43, 0xee, 0x3d, 0x27, + 0xf4, 0x1b, 0xee, 0x4a, 0x98, 0x0d, 0xe5, 0x16, 0xad, 0x8d, 0x79, 0x23, 0x35, 0xaa, 0xf1, 0x60, + 0x97, 0xa8, 0xc6, 0x36, 0x8c, 0xb4, 0xd8, 0x32, 0xf4, 0x95, 0x46, 0x2d, 0xb6, 0xa0, 0x6a, 0xa2, + 0x5d, 0x86, 0x19, 0x4b, 0x12, 0xf4, 0x84, 0x77, 0xa4, 0x55, 0x40, 0x3d, 0xe1, 0x43, 0x53, 0x01, + 0x8e, 0xe0, 0x68, 0x37, 0x1e, 0x2e, 0x7b, 0xa4, 0xb8, 0x2d, 0x4c, 0x74, 0x4f, 0x89, 0x90, 0xcd, + 0xa7, 0x3e, 0x2f, 0x64, 0x36, 0xfa, 0x19, 0x0d, 0xce, 0x9b, 0xd9, 0xb9, 0x3f, 0xd8, 0xa1, 0x5e, + 0xf0, 0xe1, 0x59, 0x4e, 0x3a, 0x91, 0xc5, 0xb2, 0x98, 0xb0, 0xbc, 0x7c, 0x23, 0x38, 0xaf, 0x33, + 0xfa, 0xf7, 0x0f, 0x86, 0x5f, 0x93, 0xd0, 0x96, 0xb3, 0x6d, 0x19, 0x5a, 0x11, 0x5b, 0x06, 0xfa, + 0x26, 0x99, 0xe3, 0xa3, 0x14, 0xcb, 0x5e, 0x1d, 0xe6, 0xf8, 0x98, 0x10, 0xa4, 0x63, 0x79, 0x3d, + 0x3a, 0x70, 0xda, 0x0f, 0x0c, 0x9b, 0xd4, 0x2d, 0x71, 0x81, 0xe2, 0x07, 0x46, 0xab, 0x5d, 0x20, + 0xc9, 0x06, 0x7f, 0x88, 0x9a, 0x46, 0x85, 0xb3, 0xf0, 0xa3, 0xef, 0x66, 0xc1, 0x7d, 0x0c, 0x9b, + 0x5d, 0x30, 0xf1, 0x74, 0x58, 0x11, 0xf1, 0xc3, 0xbb, 0x3f, 0x8a, 0xd0, 0x3d, 0xd9, 0xf8, 0x70, + 0x2e, 0x25, 0xf4, 0x26, 0x9c, 0xa5, 0xa2, 0xc2, 0x42, 0x23, 0xb0, 0xb6, 0xad, 0x60, 0x37, 0xea, + 0xc2, 0xe1, 0x33, 0x6b, 0x30, 0x8d, 0x6d, 0x39, 0x0b, 0x19, 0xce, 0xa6, 0xa1, 0xff, 0x89, 0x06, + 0x28, 0xbd, 0xd7, 0x91, 0x0d, 0xa3, 0xa6, 0x7c, 0x19, 0xaa, 0x1d, 0x49, 0xd0, 0xf9, 0xf0, 0x08, + 0x09, 0x1f, 0x94, 0x86, 0x14, 0x90, 0x0b, 0x63, 0xf7, 0xb6, 0xac, 0x80, 0xd8, 0x96, 0x1f, 0x1c, + 0x51, 0x8c, 0xfb, 0x30, 0xa4, 0xf1, 0x1d, 0x89, 0x18, 0x47, 0x34, 0xf4, 0x1f, 0x18, 0x84, 0xd1, + 0x30, 0xaf, 0xd3, 0xc1, 0x4e, 0x6f, 0x1d, 0x40, 0x0d, 0x25, 0x37, 0x76, 0x3f, 0x76, 0x37, 0x26, + 0x2d, 0x56, 0x52, 0xc8, 0x70, 0x06, 0x01, 0xf4, 0x26, 0x9c, 0xb1, 0x9c, 0x4d, 0xcf, 0x08, 0xc3, + 0x29, 0xf5, 0x93, 0x62, 0x9a, 0x29, 0x7b, 0xb5, 0x0c, 0x74, 0x38, 0x93, 0x08, 0x22, 0x30, 0xc2, + 0xd3, 0xd7, 0x49, 0xcb, 0xfa, 0xd5, 0x42, 0xc1, 0xe8, 0x18, 0x8a, 0x88, 0xbd, 0xf3, 0xdf, 0x3e, + 0x96, 0xb8, 0x79, 0xf0, 0x3b, 0xfe, 0xbf, 0xbc, 0x74, 0x10, 0xfb, 0xbe, 0x52, 0x9c, 0x5e, 0x74, + 0x7f, 0xc1, 0x83, 0xdf, 0xc5, 0x0b, 0x71, 0x92, 0xa0, 0xfe, 0xab, 0x1a, 0x0c, 0xf1, 0x18, 0x27, + 0xc7, 0x2f, 0x6a, 0x7e, 0x47, 0x4c, 0xd4, 0x2c, 0x94, 0x25, 0x97, 0x75, 0x35, 0x37, 0x7f, 0xeb, + 0x97, 0x35, 0x18, 0x63, 0x35, 0x4e, 0x40, 0xf6, 0x7b, 0x2d, 0x2e, 0xfb, 0x3d, 0x57, 0x78, 0x34, + 0x39, 0x92, 0xdf, 0xaf, 0x0e, 0x88, 0xb1, 0x30, 0xd1, 0xaa, 0x06, 0xa7, 0xc5, 0x9b, 0xa9, 0x65, + 0x6b, 0x93, 0xd0, 0x2d, 0x5e, 0x35, 0x76, 0xb9, 0xdf, 0xc9, 0x90, 0x78, 0x54, 0x9f, 0x06, 0xe3, + 0xac, 0x36, 0xe8, 0x97, 0x35, 0x2a, 0xc4, 0x04, 0x9e, 0xd5, 0xe8, 0xeb, 0xc2, 0x2f, 0xec, 0xdb, + 0xfc, 0x0a, 0x47, 0xc6, 0x55, 0xa8, 0xdb, 0x91, 0x34, 0xc3, 0x4a, 0x1f, 0xec, 0x95, 0xcb, 0x19, + 0x76, 0xc7, 0x28, 0x41, 0xa2, 0x1f, 0x7c, 0xfc, 0xf7, 0xbb, 0x56, 0x61, 0xb7, 0xdf, 0xb2, 0xc7, + 0xe8, 0x06, 0x0c, 0xf9, 0x0d, 0xb7, 0x4d, 0x0e, 0x93, 0xe6, 0x39, 0x9c, 0xe0, 0x3a, 0x6d, 0x89, + 0x39, 0x82, 0xb9, 0xd7, 0x61, 0x42, 0xed, 0x79, 0x86, 0x8a, 0x56, 0x55, 0x55, 0xb4, 0x43, 0x3b, + 0xd0, 0xa8, 0x2a, 0xdd, 0xef, 0x0c, 0xc0, 0x30, 0x26, 0x4d, 0x91, 0x51, 0xe4, 0x80, 0x3b, 0x7e, + 0x4b, 0x66, 0xa2, 0x2b, 0x15, 0x7f, 0x97, 0xa1, 0xc6, 0x8c, 0x7f, 0xd5, 0x75, 0x94, 0x39, 0x50, + 0x93, 0xd1, 0x21, 0x27, 0xcc, 0xb3, 0x30, 0x50, 0x3c, 0x15, 0x2d, 0x1f, 0x58, 0x2f, 0x99, 0x15, + 0xd0, 0x0f, 0x6b, 0x80, 0x8c, 0x46, 0x83, 0xf8, 0x3e, 0x26, 0x3e, 0x9d, 0x7b, 0x2e, 0xac, 0x72, + 0x2e, 0x5b, 0x2c, 0xea, 0x66, 0x12, 0x5b, 0x24, 0xb6, 0xa5, 0x40, 0x3e, 0xce, 0x20, 0xde, 0x4f, + 0xb6, 0x87, 0xdf, 0xd0, 0x60, 0x22, 0x96, 0x4c, 0xa3, 0x15, 0xd9, 0x63, 0x8b, 0xbb, 0x65, 0xc8, + 0xd7, 0x00, 0x0f, 0x77, 0xa9, 0xc4, 0x6d, 0xbc, 0xb7, 0xc2, 0x70, 0xda, 0x47, 0x93, 0x77, 0x43, + 0xff, 0x8c, 0x06, 0xe7, 0xe4, 0x80, 0xe2, 0x71, 0x53, 0xd1, 0x13, 0x30, 0x6a, 0xb4, 0x2d, 0x66, + 0x8f, 0x54, 0x2d, 0xba, 0x0b, 0x6b, 0x35, 0x56, 0x86, 0x43, 0x68, 0x2c, 0xdd, 0x5f, 0xe9, 0xc0, + 0x74, 0x7f, 0x8f, 0x2b, 0x09, 0x0c, 0x87, 0x22, 0xd9, 0x25, 0x24, 0xcc, 0x1d, 0xde, 0xf4, 0xf7, + 0xc1, 0x58, 0xbd, 0x7e, 0x83, 0x2f, 0xe9, 0x21, 0x6e, 0x0d, 0xf4, 0x4f, 0x0e, 0xc0, 0xa4, 0x08, + 0x00, 0x6d, 0x39, 0xa6, 0xe5, 0x34, 0x4f, 0xe0, 0x9c, 0x5b, 0x87, 0x31, 0x6e, 0x0a, 0x3a, 0x20, + 0xc9, 0x7d, 0x5d, 0x56, 0x4a, 0x26, 0xa1, 0x09, 0x01, 0x38, 0x42, 0x84, 0x6e, 0xc2, 0xf0, 0x1b, + 0x94, 0xe7, 0xca, 0x6f, 0xb5, 0x27, 0xd6, 0x17, 0x7e, 0x88, 0x8c, 0x5d, 0xfb, 0x58, 0xa0, 0x40, + 0x3e, 0x7b, 0xae, 0xc2, 0x84, 0xc0, 0x7e, 0x42, 0x91, 0xc5, 0x66, 0x36, 0x4c, 0x5f, 0x3a, 0x21, + 0x5e, 0xbd, 0xb0, 0x5f, 0x38, 0x24, 0xc4, 0x32, 0x68, 0xc5, 0x5a, 0xbc, 0x4d, 0x32, 0x68, 0xc5, + 0xfa, 0x9c, 0x73, 0x5c, 0x3f, 0x07, 0x67, 0x33, 0x27, 0xe3, 0x60, 0x11, 0x5b, 0xff, 0x27, 0x25, + 0x18, 0xac, 0x13, 0x62, 0x9e, 0xc0, 0xce, 0x7c, 0x2d, 0x26, 0x81, 0x7d, 0x73, 0xe1, 0x1c, 0x5e, + 0x79, 0x96, 0xbe, 0xcd, 0x84, 0xa5, 0xef, 0xc5, 0xc2, 0x14, 0xba, 0x9b, 0xf9, 0x7e, 0xa2, 0x04, + 0x40, 0xab, 0x2d, 0x1a, 0x8d, 0xbb, 0x9c, 0xe3, 0x84, 0xbb, 0x39, 0x91, 0x60, 0x34, 0xbd, 0x0d, + 0x4f, 0xd2, 0x8d, 0x40, 0x87, 0x61, 0x8f, 0x9d, 0x8e, 0xe2, 0xd2, 0x88, 0x99, 0x8b, 0xf9, 0x79, + 0x89, 0x05, 0x24, 0xce, 0x2d, 0x06, 0x8f, 0x88, 0x5b, 0xe8, 0x3b, 0x30, 0x42, 0x27, 0xa8, 0xba, + 0x5a, 0x47, 0x2d, 0x65, 0x76, 0x4a, 0xc5, 0xf5, 0x0b, 0x81, 0xee, 0xc0, 0xaf, 0xfc, 0x93, 0x1a, + 0x9c, 0x4a, 0xd4, 0xed, 0x41, 0xcf, 0x3c, 0x16, 0x9e, 0xa9, 0xff, 0x8a, 0x06, 0xa3, 0xb4, 0x2f, + 0x27, 0xc0, 0x68, 0xbe, 0x3d, 0xce, 0x68, 0xde, 0x5f, 0x74, 0x8a, 0x73, 0xf8, 0xcb, 0x1f, 0x95, + 0x80, 0x25, 0xcb, 0x13, 0xfe, 0x1e, 0x8a, 0x27, 0x87, 0x96, 0xe3, 0x83, 0x72, 0x49, 0x38, 0x82, + 0x24, 0x0c, 0xbc, 0x8a, 0x33, 0xc8, 0xbb, 0x63, 0xbe, 0x1e, 0xb1, 0xcf, 0x26, 0xc3, 0xdf, 0xe3, + 0x3e, 0x4c, 0xfa, 0x5b, 0xae, 0x1b, 0x84, 0x61, 0xb3, 0x06, 0x8b, 0x1b, 0xf3, 0xd9, 0x33, 0x38, + 0x39, 0x14, 0x7e, 0x7b, 0x57, 0x57, 0x71, 0xe3, 0x38, 0x29, 0x34, 0x0f, 0xb0, 0x61, 0xbb, 0x8d, + 0xbb, 0xdc, 0xd5, 0x84, 0x3f, 0x7b, 0x62, 0x97, 0xd9, 0x8b, 0x61, 0x29, 0x56, 0x6a, 0xf4, 0xe5, + 0x55, 0xf3, 0x07, 0x1a, 0x9f, 0xe9, 0x43, 0x6c, 0xde, 0x13, 0xe4, 0x28, 0xef, 0x4a, 0x70, 0x94, + 0x90, 0x43, 0x26, 0xb8, 0x4a, 0x59, 0x2a, 0x11, 0x83, 0x91, 0xf1, 0x3e, 0x96, 0x87, 0xfa, 0x17, + 0xc5, 0x30, 0xc3, 0x7c, 0x8b, 0x6d, 0x98, 0xb4, 0xd5, 0x0c, 0xca, 0xe2, 0x1b, 0x29, 0x94, 0x7c, + 0x39, 0x74, 0x63, 0x8c, 0x15, 0xe3, 0x38, 0x01, 0xf4, 0x2c, 0x4c, 0xca, 0xd1, 0x71, 0x6f, 0xc2, + 0x52, 0xf4, 0x26, 0x69, 0x4d, 0x05, 0xe0, 0x78, 0x3d, 0xfd, 0xad, 0x12, 0x3c, 0xc2, 0xfb, 0xce, + 0xac, 0x18, 0x55, 0xd2, 0x26, 0x8e, 0x49, 0x9c, 0xc6, 0x2e, 0x93, 0x59, 0x4d, 0xb7, 0x89, 0xde, + 0x84, 0xe1, 0x7b, 0x84, 0x98, 0xe1, 0x75, 0xc0, 0x9d, 0xe2, 0xe9, 0x2a, 0x73, 0x48, 0xdc, 0x61, + 0xe8, 0x39, 0x47, 0xe7, 0xff, 0x63, 0x41, 0x92, 0x12, 0x6f, 0x7b, 0xee, 0x46, 0x28, 0x5a, 0x1d, + 0x3d, 0xf1, 0x35, 0x86, 0x9e, 0x13, 0xe7, 0xff, 0x63, 0x41, 0x52, 0x5f, 0x83, 0x47, 0x7b, 0x68, + 0x7a, 0x18, 0x11, 0xfa, 0x20, 0x8c, 0x7c, 0xf4, 0x87, 0xc1, 0xf8, 0xbb, 0x1a, 0x3c, 0xa6, 0xa0, + 0x5c, 0xda, 0xa1, 0x52, 0x7d, 0xc5, 0x68, 0x1b, 0x0d, 0xaa, 0x37, 0xb3, 0x50, 0x40, 0x87, 0x4a, + 0x10, 0xf7, 0x49, 0x0d, 0x46, 0xb8, 0x87, 0x94, 0x64, 0xbf, 0xaf, 0xf5, 0x39, 0xe5, 0xb9, 0x5d, + 0x92, 0x99, 0x47, 0xe4, 0xd8, 0xf8, 0x6f, 0x1f, 0x4b, 0xfa, 0xfa, 0xbf, 0x19, 0x82, 0x6f, 0xe8, + 0x1d, 0x11, 0xfa, 0x03, 0x2d, 0x99, 0xbf, 0x79, 0xfc, 0x4a, 0xeb, 0x78, 0x3b, 0x1f, 0x5a, 0x56, + 0x84, 0xb2, 0x7e, 0x27, 0x95, 0xfb, 0xf2, 0x88, 0x8c, 0x36, 0xd1, 0xc0, 0xd0, 0x3f, 0xd4, 0x60, + 0x82, 0x1e, 0x4b, 0xf5, 0x28, 0xb3, 0x3b, 0x1d, 0x69, 0xfb, 0x98, 0x47, 0xba, 0xaa, 0x90, 0x4c, + 0xc4, 0x0c, 0x51, 0x41, 0x38, 0xd6, 0x37, 0x74, 0x3b, 0x7e, 0x95, 0xc6, 0xd5, 0xad, 0x8b, 0x59, + 0xd2, 0xc8, 0x61, 0x32, 0xcb, 0xce, 0xd9, 0x30, 0x15, 0x9f, 0xf9, 0xe3, 0x34, 0x39, 0xcd, 0xbd, + 0x04, 0x33, 0xa9, 0xd1, 0x1f, 0xca, 0xb8, 0xf1, 0x77, 0x86, 0xa0, 0xac, 0x4c, 0x75, 0xd6, 0xc3, + 0x7b, 0xf4, 0x39, 0x0d, 0xc6, 0x0d, 0xc7, 0x11, 0xbe, 0x2c, 0x72, 0xff, 0x9a, 0x7d, 0xae, 0x6a, + 0x16, 0xa9, 0xf9, 0x85, 0x88, 0x4c, 0xc2, 0x59, 0x43, 0x81, 0x60, 0xb5, 0x37, 0x5d, 0xbc, 0x25, + 0x4b, 0x27, 0xe6, 0x2d, 0x89, 0x3e, 0x22, 0x0f, 0x62, 0xbe, 0x8d, 0x5e, 0x39, 0x86, 0xb9, 0x61, + 0xe7, 0x7a, 0x8e, 0x85, 0xef, 0x07, 0x35, 0x76, 0xc8, 0x46, 0xf1, 0x11, 0xc4, 0x99, 0x54, 0xc8, + 0xaf, 0xee, 0xc0, 0xe0, 0x0b, 0xe1, 0xd9, 0x1d, 0x15, 0xe1, 0x38, 0xf9, 0xb9, 0x17, 0x61, 0x3a, + 0xb9, 0x94, 0x87, 0xda, 0x96, 0xff, 0x6a, 0x30, 0x76, 0x76, 0xe4, 0xce, 0x47, 0x0f, 0x86, 0xd6, + 0xcf, 0x27, 0x76, 0x2f, 0xe7, 0x49, 0xd6, 0x71, 0xad, 0xd0, 0xd1, 0x6e, 0xe1, 0x81, 0x93, 0xdb, + 0xc2, 0xff, 0xdf, 0xed, 0xa1, 0x45, 0x38, 0xab, 0x2c, 0x98, 0x92, 0xeb, 0xfc, 0x49, 0x18, 0xd9, + 0xb6, 0x7c, 0x4b, 0x86, 0xb1, 0x54, 0x64, 0x98, 0x97, 0x79, 0x31, 0x96, 0x70, 0x7d, 0x39, 0xc6, + 0x1d, 0xd7, 0xdd, 0xb6, 0x6b, 0xbb, 0xcd, 0xdd, 0x85, 0x7b, 0x86, 0x47, 0xb0, 0xdb, 0x09, 0x04, + 0xb6, 0x5e, 0x25, 0xa2, 0x15, 0xb8, 0xa4, 0x60, 0xcb, 0x0c, 0xf6, 0x75, 0x18, 0x74, 0xbf, 0x3e, + 0x22, 0x85, 0x7b, 0x11, 0xf8, 0xe3, 0x17, 0x34, 0x78, 0x88, 0xe4, 0x1d, 0x96, 0x42, 0xd2, 0x7f, + 0xe5, 0xb8, 0x0e, 0x63, 0x91, 0x58, 0x20, 0x0f, 0x8c, 0xf3, 0x7b, 0x86, 0x76, 0x63, 0x19, 0xff, + 0x4b, 0xfd, 0x58, 0x2a, 0x33, 0xd6, 0xbb, 0x5b, 0xbe, 0x7f, 0xf4, 0x93, 0x1a, 0x9c, 0xb1, 0x33, + 0x36, 0xab, 0xd8, 0xfc, 0xf5, 0x63, 0x60, 0x13, 0xfc, 0xa6, 0x3a, 0x0b, 0x82, 0x33, 0xbb, 0x82, + 0x7e, 0x3a, 0x37, 0x0a, 0x1d, 0xbf, 0x48, 0x5e, 0xef, 0xb3, 0x93, 0x47, 0x15, 0x90, 0xee, 0x2d, + 0x0d, 0x90, 0x99, 0x52, 0x1c, 0x84, 0x93, 0xd2, 0x87, 0x8e, 0x5c, 0x3d, 0xe2, 0xae, 0x06, 0xe9, + 0x72, 0x9c, 0xd1, 0x09, 0xb6, 0xce, 0x41, 0xc6, 0xe7, 0x2b, 0x9e, 0x7b, 0xf5, 0xbb, 0xce, 0x59, + 0x9c, 0x81, 0xaf, 0x73, 0x16, 0x04, 0x67, 0x76, 0x45, 0xff, 0xdd, 0x11, 0x6e, 0xc7, 0x62, 0x77, + 0xc1, 0x1b, 0x30, 0xbc, 0xc1, 0xec, 0x9e, 0xe2, 0xbb, 0x2d, 0x6c, 0x64, 0xe5, 0xd6, 0x53, 0xae, + 0x45, 0xf2, 0xff, 0xb1, 0xc0, 0x8c, 0x5e, 0x85, 0x01, 0xd3, 0x91, 0x2f, 0x2a, 0x9f, 0xef, 0xc3, + 0x5c, 0x18, 0xbd, 0xeb, 0xae, 0xae, 0xd6, 0x31, 0x45, 0x8a, 0x1c, 0x18, 0x75, 0x84, 0xe9, 0x47, + 0x68, 0xe7, 0x1f, 0x28, 0x4a, 0x20, 0x34, 0x21, 0x85, 0x86, 0x2b, 0x59, 0x82, 0x43, 0x1a, 0x94, + 0x5e, 0xe2, 0xae, 0xa3, 0x30, 0xbd, 0xd0, 0xf8, 0xd9, 0xcd, 0xbe, 0x4c, 0x60, 0x38, 0x30, 0x2c, + 0x27, 0x90, 0xaf, 0x23, 0x5f, 0x28, 0x4a, 0x6d, 0x9d, 0x62, 0x89, 0x2c, 0x3c, 0xec, 0xa7, 0x8f, + 0x05, 0x72, 0x96, 0x2c, 0x9e, 0xbd, 0x90, 0x14, 0x9f, 0x51, 0xe1, 0x6d, 0xc0, 0x1f, 0x5d, 0x8a, + 0x64, 0xf1, 0xec, 0x7f, 0x2c, 0x30, 0xa3, 0xd7, 0x61, 0xd4, 0x97, 0xae, 0x29, 0xa3, 0xfd, 0x4d, + 0x5d, 0xe8, 0x97, 0x22, 0xde, 0x93, 0x09, 0x87, 0x94, 0x10, 0x3f, 0xda, 0x80, 0x11, 0x8b, 0x3f, + 0x85, 0x12, 0x21, 0x34, 0x9f, 0xef, 0x23, 0xb1, 0x33, 0x37, 0x14, 0x88, 0x1f, 0x58, 0x22, 0xce, + 0xbb, 0x7f, 0x86, 0xaf, 0xe1, 0xfd, 0xb3, 0xfe, 0xeb, 0xc0, 0xef, 0x32, 0x84, 0x47, 0xe2, 0x26, + 0x8c, 0x4a, 0x92, 0xfd, 0x84, 0x21, 0xb8, 0x2e, 0xc0, 0x7c, 0xba, 0xe5, 0x2f, 0x1c, 0xe2, 0x46, + 0x95, 0xac, 0x70, 0x12, 0x51, 0x76, 0xac, 0xde, 0x42, 0x49, 0xbc, 0xc1, 0xf2, 0x71, 0xcb, 0x70, + 0x54, 0x03, 0xc5, 0xb7, 0x7b, 0x18, 0xaa, 0x2a, 0x96, 0x87, 0x5b, 0x46, 0xb3, 0x52, 0x88, 0xe4, + 0x78, 0x6c, 0x0e, 0x16, 0xf2, 0xd8, 0x7c, 0x01, 0x4e, 0x09, 0x0f, 0x99, 0x9a, 0x49, 0x98, 0x06, + 0x2d, 0xde, 0xde, 0x30, 0xdf, 0xa9, 0x4a, 0x1c, 0x84, 0x93, 0x75, 0xd1, 0xbf, 0xd4, 0x60, 0xb4, + 0x21, 0x84, 0x16, 0xf1, 0xad, 0x2f, 0xf7, 0x77, 0xe1, 0x35, 0x2f, 0x65, 0x20, 0xae, 0x1f, 0xbc, + 0x2c, 0xb9, 0x8c, 0x2c, 0x3e, 0x22, 0xc3, 0x4c, 0xd8, 0x6b, 0xf4, 0x6b, 0x54, 0x05, 0xb2, 0x6d, + 0xb7, 0x61, 0xf0, 0x04, 0xde, 0xfc, 0x51, 0xd0, 0xad, 0x3e, 0x47, 0xb1, 0x10, 0x61, 0xe4, 0x03, + 0xf9, 0x96, 0x50, 0xd1, 0x89, 0x20, 0x47, 0x34, 0x16, 0xb5, 0xfb, 0xe8, 0xef, 0x6b, 0xf0, 0x18, + 0x7f, 0x89, 0x55, 0xa1, 0x72, 0x08, 0x8b, 0x48, 0x48, 0x78, 0x80, 0x27, 0xf9, 0x10, 0x85, 0xfb, + 0x97, 0x8e, 0x1e, 0xda, 0xbf, 0xf4, 0x89, 0xfd, 0xbd, 0xf2, 0x63, 0x95, 0x1e, 0x70, 0xe3, 0x9e, + 0x7a, 0x80, 0xee, 0xc3, 0xa4, 0xad, 0xc6, 0x6a, 0x14, 0x4c, 0xaf, 0xd0, 0x75, 0x4a, 0x2c, 0xe8, + 0x23, 0xd7, 0x9f, 0x62, 0x45, 0x38, 0x4e, 0x6a, 0xee, 0x2e, 0x4c, 0xc6, 0x36, 0xda, 0xb1, 0x1a, + 0xa2, 0x1c, 0x98, 0x4e, 0xee, 0x87, 0x63, 0xf5, 0xb5, 0xba, 0x09, 0x63, 0xe1, 0xe1, 0x89, 0x1e, + 0x51, 0x08, 0x45, 0xa2, 0xc8, 0x4d, 0xb2, 0xcb, 0xa9, 0x96, 0x63, 0x2a, 0x22, 0xbf, 0x25, 0x79, + 0x99, 0x16, 0x08, 0x84, 0xfa, 0x6f, 0x8a, 0x5b, 0x92, 0x75, 0xd2, 0x6a, 0xdb, 0x46, 0x40, 0xde, + 0xfe, 0x77, 0xf4, 0xfa, 0x7f, 0xd5, 0xf8, 0x79, 0xc3, 0x8f, 0x7a, 0x64, 0xc0, 0x78, 0x8b, 0xe7, + 0x0c, 0x61, 0xb1, 0xa2, 0xb4, 0xe2, 0x51, 0xaa, 0x56, 0x22, 0x34, 0x58, 0xc5, 0x89, 0xee, 0xc1, + 0x98, 0x14, 0x8e, 0xa4, 0x91, 0xe5, 0x5a, 0x7f, 0xc2, 0x4a, 0x28, 0x87, 0x85, 0xd7, 0xbf, 0xb2, + 0xc4, 0xc7, 0x11, 0x2d, 0xdd, 0x00, 0x94, 0x6e, 0x43, 0xf5, 0x68, 0xf9, 0xd6, 0x43, 0x8b, 0x47, + 0xf9, 0x4e, 0xbd, 0xf7, 0x90, 0x36, 0xa4, 0x52, 0x9e, 0x0d, 0x49, 0xff, 0x62, 0x09, 0x32, 0x13, + 0x5e, 0x23, 0x1d, 0x86, 0xf9, 0xf3, 0x4b, 0x41, 0x84, 0x89, 0x57, 0xfc, 0x6d, 0x26, 0x16, 0x10, + 0x74, 0x8b, 0x1b, 0x77, 0x1c, 0x93, 0x45, 0xd7, 0x8e, 0xb8, 0x84, 0xfa, 0x08, 0x79, 0x29, 0xab, + 0x02, 0xce, 0x6e, 0x87, 0xb6, 0x01, 0xb5, 0x8c, 0x9d, 0x24, 0xb6, 0x3e, 0x72, 0x90, 0xae, 0xa4, + 0xb0, 0xe1, 0x0c, 0x0a, 0xf4, 0x20, 0xa5, 0x92, 0x4d, 0x3b, 0x20, 0x26, 0x1f, 0xa2, 0xbc, 0xa4, + 0x65, 0x07, 0xe9, 0x42, 0x1c, 0x84, 0x93, 0x75, 0xf5, 0xaf, 0x0e, 0xc2, 0x43, 0xf1, 0x49, 0xa4, + 0x5f, 0xa8, 0x7c, 0x21, 0xf9, 0x92, 0x7c, 0x57, 0xc1, 0x27, 0xf2, 0xc9, 0xe4, 0xbb, 0x8a, 0xd9, + 0x8a, 0x47, 0xd8, 0x91, 0x6c, 0xd8, 0xbe, 0x6c, 0x14, 0x7b, 0x63, 0xf1, 0x35, 0x78, 0xee, 0x98, + 0xf3, 0xac, 0x73, 0xe0, 0x58, 0x9f, 0x75, 0x7e, 0x4a, 0x83, 0xb9, 0x78, 0xf1, 0x35, 0xcb, 0xb1, + 0xfc, 0x2d, 0x11, 0x23, 0xfa, 0xf0, 0xcf, 0x3a, 0x58, 0xd6, 0xb4, 0xe5, 0x5c, 0x8c, 0xb8, 0x0b, + 0x35, 0xf4, 0x69, 0x0d, 0x1e, 0x4e, 0xcc, 0x4b, 0x2c, 0x62, 0xf5, 0xe1, 0x5f, 0x78, 0xb0, 0xc7, + 0xf3, 0xcb, 0xf9, 0x28, 0x71, 0x37, 0x7a, 0xfa, 0x3f, 0x2d, 0xc1, 0x10, 0xf3, 0x31, 0x78, 0x7b, + 0x38, 0xba, 0xb3, 0xae, 0xe6, 0xfa, 0x59, 0x35, 0x13, 0x7e, 0x56, 0x2f, 0x15, 0x27, 0xd1, 0xdd, + 0xd1, 0xea, 0x5b, 0xe0, 0x1c, 0xab, 0xb6, 0x60, 0x32, 0xc3, 0x8e, 0x4f, 0xcc, 0x05, 0xd3, 0x64, + 0xaa, 0xd4, 0xc1, 0xe6, 0xf5, 0x47, 0x60, 0xa0, 0xe3, 0xd9, 0xc9, 0xf0, 0x6e, 0xb7, 0xf1, 0x32, + 0xa6, 0xe5, 0xfa, 0xa7, 0x34, 0x98, 0x66, 0xb8, 0x95, 0xcf, 0x17, 0x6d, 0xc3, 0xa8, 0x27, 0x3e, + 0x61, 0xb1, 0x36, 0xcb, 0x85, 0x87, 0x96, 0xc1, 0x16, 0x44, 0x4a, 0x7e, 0xf1, 0x0b, 0x87, 0xb4, + 0xf4, 0xaf, 0x0c, 0xc3, 0x6c, 0x5e, 0x23, 0xf4, 0x23, 0x1a, 0x9c, 0x6b, 0x44, 0xd2, 0x9c, 0x48, + 0xec, 0x1d, 0x58, 0xc2, 0xf9, 0xa6, 0xa0, 0xea, 0x5d, 0x59, 0x08, 0x7b, 0xc5, 0x82, 0x09, 0x57, + 0x32, 0x29, 0xe0, 0x1c, 0xca, 0xe8, 0x4d, 0x1e, 0xfa, 0xaa, 0xa1, 0xfa, 0x9b, 0xdc, 0x2c, 0x3c, + 0x57, 0x4a, 0xda, 0x07, 0xd9, 0xa9, 0x30, 0xfe, 0x95, 0x28, 0x57, 0xc8, 0x51, 0xe2, 0xbe, 0xbf, + 0x75, 0x93, 0xec, 0xb6, 0x0d, 0x4b, 0xba, 0x58, 0x14, 0x27, 0x5e, 0xaf, 0xdf, 0x10, 0xa8, 0xe2, + 0xc4, 0x95, 0x72, 0x85, 0x1c, 0xfa, 0xb8, 0x06, 0x93, 0xae, 0xfa, 0x96, 0xbe, 0x1f, 0x0f, 0xd6, + 0xcc, 0x47, 0xf9, 0x5c, 0x84, 0x8e, 0x83, 0xe2, 0x24, 0xe9, 0x9e, 0x98, 0xf1, 0x93, 0x47, 0x96, + 0x60, 0x6a, 0x2b, 0xc5, 0x84, 0x9b, 0x9c, 0xf3, 0x8f, 0xab, 0xe3, 0x69, 0x70, 0x9a, 0x3c, 0xeb, + 0x14, 0x09, 0x1a, 0x66, 0x94, 0xdd, 0x9f, 0x76, 0x6a, 0xb8, 0x78, 0xa7, 0x96, 0xd6, 0x2b, 0xd5, + 0x18, 0xb2, 0x78, 0xa7, 0xd2, 0xe0, 0x34, 0x79, 0xfd, 0x63, 0x25, 0x38, 0x9f, 0xb3, 0xc7, 0xfe, + 0xca, 0x04, 0x3f, 0xf8, 0xb2, 0x06, 0x63, 0x6c, 0x0e, 0xde, 0x26, 0x0f, 0x93, 0x58, 0x5f, 0x73, + 0x3c, 0x11, 0x7f, 0x45, 0x83, 0x99, 0x54, 0x18, 0xfb, 0x9e, 0x9e, 0xb5, 0x9c, 0x98, 0x93, 0xdc, + 0xe3, 0x51, 0x1e, 0x9f, 0x81, 0xe8, 0x35, 0x77, 0x32, 0x87, 0x8f, 0x7e, 0x07, 0x26, 0x63, 0x8e, + 0x88, 0x4a, 0xec, 0xac, 0xac, 0xa8, 0x5f, 0x6a, 0x68, 0xac, 0x52, 0xb7, 0xa0, 0x5e, 0xd1, 0x96, + 0x4f, 0x73, 0xb6, 0xbf, 0x3a, 0x5b, 0x1e, 0x89, 0x2d, 0xcf, 0xee, 0x2c, 0x5e, 0x83, 0x61, 0x16, + 0x91, 0x4b, 0x9e, 0x98, 0x57, 0x0b, 0x47, 0xfa, 0xf2, 0xb9, 0x26, 0xc5, 0xff, 0xc7, 0x02, 0x2b, + 0x4b, 0xd0, 0xae, 0xc4, 0xa9, 0x5b, 0x8d, 0x94, 0xb6, 0x33, 0xc9, 0xa8, 0x76, 0x6c, 0x4b, 0xa6, + 0x6a, 0x23, 0xcc, 0x6f, 0x3c, 0xf8, 0x59, 0x56, 0x28, 0xf0, 0x7a, 0x75, 0xb5, 0xce, 0x03, 0x27, + 0x85, 0x37, 0x1d, 0x6f, 0x00, 0x10, 0xb9, 0x71, 0xe5, 0x2b, 0xa7, 0x17, 0x8a, 0xc5, 0x28, 0x0f, + 0xb7, 0xbf, 0x14, 0x3c, 0xc3, 0x22, 0x1f, 0x2b, 0x44, 0x90, 0x07, 0xe3, 0x5b, 0xd6, 0x06, 0xf1, + 0x1c, 0x2e, 0x43, 0x0d, 0x15, 0x17, 0x0f, 0x6f, 0x44, 0x68, 0xb8, 0x7e, 0xaf, 0x14, 0x60, 0x95, + 0x08, 0xf2, 0x62, 0x51, 0x38, 0x87, 0x8b, 0x8b, 0x44, 0x91, 0xcd, 0x39, 0x1a, 0x67, 0x4e, 0x04, + 0x4e, 0x07, 0xc0, 0x09, 0x43, 0xdf, 0xf5, 0x73, 0x03, 0x12, 0x05, 0xd0, 0xe3, 0x42, 0x47, 0xf4, + 0x1b, 0x2b, 0x14, 0xe8, 0xbc, 0xb6, 0xa2, 0x48, 0xc7, 0xc2, 0x7e, 0xf8, 0x52, 0x9f, 0xd1, 0xa6, + 0x85, 0xdd, 0x24, 0x2a, 0xc0, 0x2a, 0x11, 0x3a, 0xc6, 0x56, 0x18, 0x9f, 0x58, 0xd8, 0x07, 0x0b, + 0x8d, 0x31, 0x8a, 0x72, 0x2c, 0xb2, 0xf6, 0x86, 0xbf, 0xb1, 0x42, 0x01, 0xbd, 0xae, 0x5c, 0x94, + 0x41, 0x71, 0xeb, 0x53, 0x4f, 0x97, 0x64, 0xef, 0x8d, 0x8c, 0x30, 0xe3, 0xec, 0x3b, 0x7d, 0x58, + 0x31, 0xc0, 0xb0, 0xb8, 0xcd, 0x94, 0x77, 0xa4, 0x0c, 0x32, 0x91, 0xfb, 0xf3, 0x44, 0x57, 0xf7, + 0xe7, 0x0a, 0x95, 0xce, 0x94, 0xe7, 0x38, 0x8c, 0x21, 0x4c, 0x46, 0xb7, 0x1b, 0xf5, 0x24, 0x10, + 0xa7, 0xeb, 0x73, 0x86, 0x4f, 0x4c, 0xd6, 0x76, 0x4a, 0x65, 0xf8, 0xbc, 0x0c, 0x87, 0x50, 0xb4, + 0x0d, 0x13, 0xbe, 0xe2, 0x4b, 0x2d, 0x52, 0xad, 0xf7, 0x71, 0x57, 0x26, 0xfc, 0xa8, 0x59, 0x0c, + 0x30, 0xb5, 0x04, 0xc7, 0xe8, 0xa0, 0x37, 0x55, 0xe7, 0xd1, 0xe9, 0xfe, 0xa2, 0xf7, 0xa6, 0xe3, + 0x51, 0x47, 0xd6, 0xb5, 0xd0, 0x6f, 0x51, 0xf5, 0xe9, 0xec, 0xc4, 0xdd, 0x24, 0x67, 0x8e, 0x24, + 0x78, 0xc1, 0x81, 0x6e, 0x94, 0x74, 0x69, 0xc9, 0x4e, 0xdb, 0xf5, 0x3b, 0x1e, 0x61, 0x71, 0xf6, + 0xd9, 0xf2, 0xa0, 0x68, 0x69, 0x97, 0x92, 0x40, 0x9c, 0xae, 0x8f, 0xbe, 0x57, 0x83, 0x69, 0x9e, + 0xa9, 0x9e, 0x1e, 0x5b, 0xae, 0x43, 0x9c, 0xc0, 0x67, 0xa9, 0xd8, 0x0b, 0xbe, 0xb7, 0xad, 0x27, + 0x70, 0xf1, 0x63, 0x27, 0x59, 0x8a, 0x53, 0x34, 0xe9, 0xce, 0x51, 0xc3, 0x1f, 0xb0, 0x8c, 0xee, + 0x05, 0x77, 0x8e, 0x1a, 0x5a, 0x81, 0xef, 0x1c, 0xb5, 0x04, 0xc7, 0xe8, 0xa0, 0x67, 0x61, 0xd2, + 0x97, 0x39, 0x1d, 0xd9, 0x0c, 0x9e, 0x8d, 0x02, 0xa9, 0xd5, 0x55, 0x00, 0x8e, 0xd7, 0x43, 0x1f, + 0x85, 0x09, 0xf5, 0xec, 0x14, 0x79, 0xe0, 0x8f, 0x30, 0x1e, 0x2f, 0xef, 0xb9, 0x0a, 0x8a, 0x11, + 0x44, 0x18, 0xce, 0x35, 0x22, 0x25, 0x5d, 0xfd, 0xbe, 0xcf, 0xb3, 0x21, 0x70, 0x65, 0x3a, 0xb3, + 0x06, 0xce, 0x69, 0x89, 0x7e, 0x2c, 0xfb, 0x5e, 0x78, 0x96, 0x6d, 0xe9, 0xb5, 0x23, 0xb9, 0x17, + 0xbe, 0x63, 0x05, 0x5b, 0xb7, 0xda, 0x3c, 0x9c, 0xce, 0x61, 0xaf, 0x88, 0x7f, 0x47, 0x03, 0x08, + 0xad, 0x35, 0x27, 0x71, 0x07, 0x61, 0xc6, 0x0c, 0x58, 0x8b, 0x7d, 0x59, 0x97, 0x72, 0xc3, 0xad, + 0xeb, 0xbf, 0xad, 0xc1, 0x54, 0x54, 0xed, 0x04, 0x54, 0xa3, 0x46, 0x5c, 0x35, 0x7a, 0xb1, 0xbf, + 0x71, 0xe5, 0xe8, 0x47, 0xff, 0xb7, 0xa4, 0x8e, 0x8a, 0x49, 0xbf, 0xdb, 0xb1, 0x3b, 0x7d, 0x4a, + 0xfa, 0x46, 0x3f, 0x77, 0xfa, 0xea, 0x93, 0xf3, 0x68, 0xbc, 0x19, 0x77, 0xfc, 0x7f, 0x33, 0x26, + 0x7f, 0xf6, 0x95, 0x23, 0x47, 0x60, 0x91, 0xa4, 0xf9, 0x04, 0x1c, 0x24, 0x8c, 0xbe, 0xa1, 0x1e, + 0x4f, 0x7d, 0x84, 0x48, 0x8f, 0x0d, 0xb8, 0xeb, 0xa1, 0xa4, 0x7f, 0xdf, 0x29, 0x18, 0x57, 0x0c, + 0x9b, 0x09, 0x0f, 0x05, 0xed, 0x24, 0x3c, 0x14, 0x02, 0x18, 0x6f, 0x84, 0x59, 0x8e, 0xe4, 0xb4, + 0xf7, 0x49, 0x33, 0x3c, 0x16, 0xa3, 0xfc, 0x49, 0x3e, 0x56, 0xc9, 0x50, 0xe1, 0x2d, 0xdc, 0x63, + 0x03, 0x47, 0xe0, 0x37, 0xd2, 0x6d, 0x5f, 0x3d, 0x03, 0x20, 0xe5, 0x7f, 0x62, 0x8a, 0xd0, 0xb6, + 0xe1, 0xc3, 0x8a, 0x9a, 0x7f, 0x23, 0x84, 0x61, 0xa5, 0x5e, 0xfa, 0xc6, 0x7b, 0xe8, 0xc4, 0x6e, + 0xbc, 0xe9, 0x36, 0xb0, 0x65, 0xe6, 0xd1, 0xbe, 0xfc, 0xb2, 0xc2, 0xfc, 0xa5, 0xd1, 0x36, 0x08, + 0x8b, 0x7c, 0xac, 0x10, 0xc9, 0x71, 0x54, 0x19, 0x29, 0xe4, 0xa8, 0xd2, 0x81, 0xd3, 0x1e, 0x09, + 0xbc, 0xdd, 0x8a, 0xc8, 0xde, 0x28, 0x72, 0x2b, 0x8e, 0x16, 0x8b, 0x12, 0x86, 0xd3, 0xa8, 0x70, + 0x16, 0xfe, 0x98, 0x00, 0x3c, 0xd6, 0x55, 0x00, 0x7e, 0x2f, 0x8c, 0x07, 0xa4, 0xb1, 0xe5, 0x58, + 0x0d, 0xc3, 0xae, 0x55, 0x45, 0x6c, 0xd5, 0x48, 0x96, 0x8b, 0x40, 0x58, 0xad, 0x87, 0x16, 0x61, + 0xa0, 0x63, 0x99, 0x42, 0x03, 0xf8, 0xc6, 0xf0, 0x8a, 0xa0, 0x56, 0x7d, 0xb0, 0x57, 0x7e, 0x67, + 0xe4, 0xf9, 0x11, 0x8e, 0xea, 0x72, 0xfb, 0x6e, 0xf3, 0x72, 0xb0, 0xdb, 0x26, 0xfe, 0xfc, 0xed, + 0x5a, 0x15, 0xd3, 0xc6, 0x59, 0x4e, 0x3c, 0x13, 0x87, 0x70, 0xe2, 0x79, 0x4b, 0x83, 0xd3, 0x46, + 0xf2, 0x76, 0x83, 0xf8, 0xb3, 0x93, 0xc5, 0xb9, 0x65, 0xf6, 0x8d, 0xc9, 0xe2, 0xc3, 0x62, 0x7c, + 0xa7, 0x17, 0xd2, 0xe4, 0x70, 0x56, 0x1f, 0x90, 0x07, 0xa8, 0x65, 0x35, 0xc3, 0x24, 0xa0, 0x62, + 0xd5, 0xa7, 0x8a, 0xd9, 0x6d, 0x56, 0x52, 0x98, 0x70, 0x06, 0x76, 0x74, 0x0f, 0xc6, 0x15, 0x21, + 0x49, 0x68, 0x32, 0xd5, 0xa3, 0xb8, 0x84, 0xe1, 0xda, 0xae, 0x7a, 0xc1, 0xa2, 0x52, 0x0a, 0x6f, + 0x2f, 0x15, 0x33, 0x83, 0xb8, 0xc1, 0x63, 0xa3, 0x9e, 0x2e, 0x7e, 0x7b, 0x99, 0x8d, 0x11, 0x77, + 0xa1, 0xc6, 0x62, 0x73, 0xd9, 0xf1, 0x5c, 0xbd, 0xb3, 0x33, 0xc5, 0xdf, 0xce, 0x27, 0xd2, 0xfe, + 0xf2, 0xad, 0x99, 0x28, 0xc4, 0x49, 0x82, 0xe8, 0x1a, 0x20, 0xc2, 0x4d, 0xe9, 0x91, 0x72, 0xe6, + 0xcf, 0xa2, 0x30, 0xa7, 0x31, 0x5a, 0x4a, 0x41, 0x71, 0x46, 0x0b, 0x14, 0xc4, 0x6c, 0x25, 0x7d, + 0x68, 0x39, 0xc9, 0x64, 0x03, 0xdd, 0x2c, 0x26, 0xfa, 0x6f, 0x69, 0xc2, 0xbc, 0x7a, 0x82, 0xbe, + 0x33, 0xc7, 0x7d, 0xf1, 0xaa, 0xdf, 0x81, 0xd9, 0xba, 0x8c, 0x16, 0x67, 0x26, 0x62, 0x17, 0x3f, + 0x0f, 0x93, 0xfc, 0x7a, 0x63, 0xc5, 0x68, 0xaf, 0x46, 0xb6, 0xf0, 0xf0, 0x2d, 0x74, 0x45, 0x05, + 0xe2, 0x78, 0x5d, 0xfd, 0xab, 0x1a, 0x9c, 0x8f, 0x63, 0x76, 0x3d, 0xeb, 0x7e, 0xff, 0x88, 0xd1, + 0x27, 0x34, 0x18, 0x8f, 0x6e, 0xee, 0xa4, 0x38, 0x52, 0xc8, 0xe7, 0x5e, 0xf6, 0x8a, 0x78, 0xca, + 0x55, 0x4e, 0x3a, 0x9b, 0x54, 0x04, 0xf4, 0xb1, 0x4a, 0x5a, 0xff, 0x63, 0x0d, 0x52, 0x2a, 0x31, + 0xda, 0x80, 0x11, 0x4a, 0xa4, 0xba, 0x5a, 0x17, 0x7b, 0xe2, 0xf9, 0x62, 0x92, 0x12, 0x43, 0xc1, + 0x0d, 0xfd, 0xe2, 0x07, 0x96, 0x88, 0xa9, 0x92, 0xed, 0x28, 0x59, 0x07, 0xc4, 0xf6, 0x28, 0x24, + 0x8a, 0xaa, 0xd9, 0x0b, 0xb8, 0xaa, 0xaa, 0x96, 0xe0, 0x18, 0x1d, 0x7d, 0x19, 0x20, 0x32, 0x63, + 0xf4, 0xed, 0x8b, 0xf6, 0xe3, 0xe3, 0x70, 0xb6, 0xdf, 0x97, 0x41, 0x2c, 0x11, 0x2e, 0xd9, 0xb6, + 0x1a, 0xc1, 0xc2, 0x66, 0x40, 0xbc, 0x5b, 0xb7, 0x56, 0xd6, 0xb7, 0x3c, 0xe2, 0x6f, 0xb9, 0xb6, + 0x59, 0x30, 0x13, 0x2f, 0x53, 0xb7, 0x97, 0x32, 0x31, 0xe2, 0x1c, 0x4a, 0xcc, 0x84, 0xb3, 0xcd, + 0x95, 0x5b, 0x4c, 0xf5, 0x88, 0x8e, 0xe7, 0x07, 0x22, 0x00, 0x14, 0x37, 0xe1, 0x24, 0x81, 0x38, + 0x5d, 0x3f, 0x89, 0x64, 0xd9, 0x6a, 0x59, 0x3c, 0x41, 0x81, 0x96, 0x46, 0xc2, 0x80, 0x38, 0x5d, + 0x5f, 0x45, 0xc2, 0x57, 0x8a, 0x32, 0xfa, 0xa1, 0x34, 0x92, 0x10, 0x88, 0xd3, 0xf5, 0x91, 0x09, + 0x17, 0x3c, 0xd2, 0x70, 0x5b, 0x2d, 0xe2, 0x98, 0x3c, 0xf1, 0xbe, 0xe1, 0x35, 0x2d, 0xe7, 0x9a, + 0x67, 0xb0, 0x8a, 0xcc, 0x22, 0xae, 0xb1, 0xec, 0x74, 0x17, 0x70, 0x97, 0x7a, 0xb8, 0x2b, 0x16, + 0xd4, 0x82, 0x53, 0x3c, 0xa1, 0xad, 0x57, 0x73, 0x02, 0xe2, 0x6d, 0x1b, 0xb6, 0x30, 0x7b, 0x1f, + 0x76, 0xc5, 0xd8, 0xe1, 0x73, 0x3b, 0x8e, 0x0a, 0x27, 0x71, 0xa3, 0x5d, 0x2a, 0x72, 0x8a, 0xee, + 0x28, 0x24, 0x47, 0x8b, 0xa7, 0x8a, 0xc6, 0x69, 0x74, 0x38, 0x8b, 0x06, 0xaa, 0xc1, 0xe9, 0xc0, + 0xf0, 0x9a, 0x24, 0xa8, 0xac, 0xdd, 0x5e, 0x23, 0x5e, 0x83, 0xf2, 0x58, 0x9b, 0x4b, 0xa0, 0x1a, + 0x47, 0xb5, 0x9e, 0x06, 0xe3, 0xac, 0x36, 0xe8, 0xa3, 0xf0, 0x78, 0x7c, 0x52, 0x97, 0xdd, 0x7b, + 0xc4, 0x5b, 0x74, 0x3b, 0x8e, 0x19, 0x47, 0x0e, 0x0c, 0xf9, 0x93, 0xfb, 0x7b, 0xe5, 0xc7, 0x71, + 0x2f, 0x0d, 0x70, 0x6f, 0x78, 0xd3, 0x1d, 0xb8, 0xdd, 0x6e, 0x67, 0x76, 0x60, 0x3c, 0xaf, 0x03, + 0x39, 0x0d, 0x70, 0x6f, 0x78, 0x11, 0x86, 0x73, 0x7c, 0x62, 0x78, 0x2e, 0x45, 0x85, 0xe2, 0x04, + 0xa3, 0xc8, 0xbe, 0xdf, 0xf5, 0xcc, 0x1a, 0x38, 0xa7, 0x25, 0x3d, 0x53, 0x9e, 0xc8, 0x1b, 0x7e, + 0x8a, 0xcc, 0x24, 0x23, 0xf3, 0xee, 0xfd, 0xbd, 0xf2, 0x13, 0xb8, 0xc7, 0x36, 0xb8, 0x67, 0xec, + 0x19, 0x5d, 0x89, 0x26, 0x22, 0xd5, 0x95, 0xa9, 0xbc, 0xae, 0xe4, 0xb7, 0xc1, 0x3d, 0x63, 0xd7, + 0xdf, 0xd2, 0x40, 0xbc, 0x9f, 0x41, 0x17, 0x62, 0xb7, 0xe1, 0xa3, 0x89, 0x9b, 0x70, 0x99, 0xe5, + 0xaa, 0x94, 0x99, 0xe5, 0xea, 0x5d, 0x4a, 0x40, 0xbc, 0xb1, 0x48, 0xde, 0xe1, 0x98, 0x95, 0x14, + 0xb0, 0x4f, 0xc1, 0x58, 0x28, 0xeb, 0x09, 0x1d, 0x9c, 0x45, 0x07, 0x8f, 0x84, 0xc2, 0x08, 0xae, + 0xff, 0x86, 0x06, 0x10, 0x25, 0x57, 0xeb, 0x2d, 0x71, 0xed, 0x81, 0xce, 0xaf, 0x4a, 0xc2, 0xdd, + 0x81, 0xdc, 0x84, 0xbb, 0xc7, 0x94, 0x87, 0xf6, 0x17, 0x34, 0x38, 0x15, 0x8f, 0x50, 0xe8, 0xa3, + 0xc7, 0x61, 0x44, 0xc4, 0x55, 0x16, 0x81, 0x51, 0x59, 0x53, 0x11, 0x44, 0x08, 0x4b, 0x58, 0xfc, + 0xd2, 0xa4, 0x0f, 0xa3, 0x58, 0x76, 0xa0, 0xc4, 0x03, 0xec, 0x53, 0x6f, 0xcd, 0xc0, 0x30, 0x0f, + 0xca, 0x4b, 0x8f, 0xe2, 0x8c, 0xe0, 0x09, 0x37, 0x8b, 0xc7, 0xfe, 0x2d, 0xf2, 0xc0, 0x5c, 0x4d, + 0xd4, 0x53, 0xea, 0x9a, 0xa8, 0x07, 0xf3, 0xcc, 0xe4, 0x7d, 0x5c, 0x90, 0x57, 0x70, 0x8d, 0x5f, + 0x90, 0x87, 0x59, 0xc9, 0x83, 0xd8, 0xcd, 0xf1, 0x60, 0x71, 0xcd, 0x84, 0x4f, 0x80, 0x72, 0x7f, + 0x3c, 0xd5, 0xf5, 0xee, 0x58, 0x46, 0x3d, 0x1d, 0x2a, 0xee, 0x8c, 0x2e, 0xa6, 0xbc, 0x97, 0xa8, + 0xa7, 0xf2, 0x43, 0x1a, 0xce, 0xfd, 0x90, 0x36, 0x61, 0x44, 0x7c, 0x0a, 0xe2, 0x4c, 0x7f, 0xbe, + 0x8f, 0x5c, 0x8e, 0x4a, 0x46, 0x01, 0x5e, 0x80, 0x25, 0x72, 0x2a, 0x28, 0xb6, 0x8c, 0x1d, 0xab, + 0xd5, 0x69, 0xb1, 0x83, 0x7c, 0x48, 0xad, 0xca, 0x8a, 0xb1, 0x84, 0xb3, 0xaa, 0xdc, 0x87, 0x9f, + 0x1d, 0xbc, 0x6a, 0x55, 0x5e, 0x8c, 0x25, 0x1c, 0xbd, 0x0a, 0xa3, 0x2d, 0x63, 0xa7, 0xde, 0xf1, + 0x9a, 0x44, 0xdc, 0x1b, 0xe7, 0xeb, 0x75, 0x9d, 0xc0, 0xb2, 0xe7, 0x2d, 0x27, 0xf0, 0x03, 0x6f, + 0xbe, 0xe6, 0x04, 0xb7, 0xbc, 0x7a, 0xe0, 0x85, 0xd9, 0x72, 0x57, 0x04, 0x16, 0x1c, 0xe2, 0x43, + 0x36, 0x4c, 0xb5, 0x8c, 0x9d, 0xdb, 0x8e, 0xc1, 0x03, 0xda, 0x8a, 0x83, 0xb2, 0x08, 0x05, 0xe6, + 0x38, 0xb4, 0x12, 0xc3, 0x85, 0x13, 0xb8, 0x33, 0x7c, 0x94, 0x26, 0x8e, 0xcb, 0x47, 0x69, 0x21, + 0x7c, 0x25, 0xca, 0x2d, 0x4d, 0x0f, 0x65, 0xc6, 0x97, 0xe9, 0xfa, 0x02, 0xf4, 0xb5, 0xf0, 0x05, + 0xe8, 0x54, 0x71, 0xa7, 0x9a, 0x2e, 0xaf, 0x3f, 0x3b, 0x30, 0x4e, 0xb5, 0x6a, 0x5e, 0xea, 0xcf, + 0x9e, 0x2a, 0x7e, 0x69, 0x52, 0x0d, 0xd1, 0x44, 0x2c, 0x29, 0x2a, 0xf3, 0xb1, 0x4a, 0x07, 0xdd, + 0x82, 0xb3, 0xf4, 0x63, 0xb5, 0x49, 0x10, 0x55, 0x61, 0x6a, 0xef, 0x34, 0xfb, 0x7e, 0xd8, 0xab, + 0x88, 0x9b, 0x59, 0x15, 0x70, 0x76, 0xbb, 0x28, 0x16, 0xda, 0x4c, 0x76, 0x2c, 0x34, 0xf4, 0x03, + 0x59, 0xb7, 0xc1, 0x88, 0xcd, 0xe9, 0x07, 0x8b, 0xf3, 0x86, 0xc2, 0x77, 0xc2, 0xff, 0x4c, 0x83, + 0x59, 0xb1, 0xcb, 0xc4, 0x0d, 0xae, 0x4d, 0xbc, 0x15, 0xc3, 0x31, 0x9a, 0xc4, 0x13, 0xe6, 0x9b, + 0xf5, 0x3e, 0xf8, 0x43, 0x0a, 0x67, 0xf8, 0x34, 0xf7, 0xb1, 0xfd, 0xbd, 0xf2, 0xa5, 0x83, 0x6a, + 0xe1, 0xdc, 0xbe, 0x21, 0x0f, 0x46, 0xfc, 0x5d, 0xbf, 0x11, 0xd8, 0xfe, 0xec, 0x19, 0xb6, 0x59, + 0xae, 0xf7, 0xc1, 0x59, 0xeb, 0x1c, 0x13, 0x67, 0xad, 0x51, 0x1e, 0x1b, 0x5e, 0x8a, 0x25, 0x21, + 0xf4, 0xc3, 0x1a, 0xcc, 0x08, 0x9b, 0xae, 0x12, 0xfe, 0xe0, 0x6c, 0x71, 0xdf, 0xf1, 0x4a, 0x12, + 0x99, 0xbc, 0xb5, 0x65, 0x0a, 0x61, 0x0a, 0x8a, 0xd3, 0xd4, 0xfb, 0x8d, 0x4f, 0xd2, 0x47, 0x48, + 0xea, 0xb9, 0xab, 0x30, 0xa1, 0x4e, 0xdc, 0xa1, 0xc2, 0xa2, 0xfc, 0x94, 0x06, 0xd3, 0xc9, 0x83, + 0x14, 0x6d, 0xc1, 0x88, 0xf8, 0xaa, 0x84, 0x7d, 0x66, 0xa1, 0xa8, 0x67, 0x97, 0x4d, 0xc4, 0xdb, + 0x28, 0x2e, 0x97, 0x89, 0x22, 0x2c, 0xd1, 0xab, 0x5e, 0x9b, 0xa5, 0x2e, 0x5e, 0x9b, 0x2f, 0xc0, + 0xb9, 0xec, 0xef, 0x8b, 0x4a, 0xb5, 0x86, 0x6d, 0xbb, 0xf7, 0x84, 0x11, 0x24, 0x4a, 0x09, 0x4a, + 0x0b, 0x31, 0x87, 0xe9, 0x1f, 0x81, 0x64, 0x52, 0x04, 0xf4, 0x3a, 0x8c, 0xf9, 0xfe, 0x16, 0xbf, + 0x8b, 0x17, 0x83, 0x2c, 0x66, 0x3a, 0x94, 0x01, 0xaa, 0xb9, 0x20, 0x1e, 0xfe, 0xc4, 0x11, 0xfa, + 0xc5, 0x57, 0xbe, 0xf4, 0xd5, 0x8b, 0xef, 0xf8, 0xcd, 0xaf, 0x5e, 0x7c, 0xc7, 0x57, 0xbe, 0x7a, + 0xf1, 0x1d, 0xdf, 0xb5, 0x7f, 0x51, 0xfb, 0xd2, 0xfe, 0x45, 0xed, 0x37, 0xf7, 0x2f, 0x6a, 0x5f, + 0xd9, 0xbf, 0xa8, 0xfd, 0xa7, 0xfd, 0x8b, 0xda, 0x0f, 0xfd, 0xe7, 0x8b, 0xef, 0x78, 0xf5, 0x4a, + 0x44, 0xfd, 0xb2, 0x24, 0x1a, 0xfd, 0xd3, 0xbe, 0xdb, 0xbc, 0x4c, 0xa9, 0xcb, 0x07, 0xb1, 0x8c, + 0xfa, 0xff, 0x0b, 0x00, 0x00, 0xff, 0xff, 0xfd, 0x98, 0x7a, 0x66, 0x5d, 0x0b, 0x01, 0x00, } func (m *APIServerLogging) Marshal() (dAtA []byte, err error) { @@ -7545,6 +7671,16 @@ func (m *CloudProfile) MarshalToSizedBuffer(dAtA []byte) (int, error) { _ = i var l int _ = l + { + size, err := m.Status.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintGenerated(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x1a { size, err := m.Spec.MarshalToSizedBuffer(dAtA[:i]) if err != nil { @@ -7785,6 +7921,57 @@ func (m *CloudProfileSpec) MarshalToSizedBuffer(dAtA []byte) (int, error) { return len(dAtA) - i, nil } +func (m *CloudProfileStatus) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *CloudProfileStatus) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *CloudProfileStatus) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.MachineImageVersions) > 0 { + for iNdEx := len(m.MachineImageVersions) - 1; iNdEx >= 0; iNdEx-- { + { + size, err := m.MachineImageVersions[iNdEx].MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintGenerated(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x12 + } + } + if len(m.KubernetesVersions) > 0 { + for iNdEx := len(m.KubernetesVersions) - 1; iNdEx >= 0; iNdEx-- { + { + size, err := m.KubernetesVersions[iNdEx].MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintGenerated(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + } + } + return len(dAtA) - i, nil +} + func (m *ClusterAutoscaler) Marshal() (dAtA []byte, err error) { size := m.Size() dAtA = make([]byte, size) @@ -9319,6 +9506,20 @@ func (m *ExpirableVersion) MarshalToSizedBuffer(dAtA []byte) (int, error) { _ = i var l int _ = l + if len(m.Lifecycle) > 0 { + for iNdEx := len(m.Lifecycle) - 1; iNdEx >= 0; iNdEx-- { + { + size, err := m.Lifecycle[iNdEx].MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintGenerated(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x22 + } + } if m.Classification != nil { i -= len(*m.Classification) copy(dAtA[i:], *m.Classification) @@ -9346,6 +9547,39 @@ func (m *ExpirableVersion) MarshalToSizedBuffer(dAtA []byte) (int, error) { return len(dAtA) - i, nil } +func (m *ExpirableVersionStatus) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *ExpirableVersionStatus) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *ExpirableVersionStatus) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + i -= len(m.ClassificationState) + copy(dAtA[i:], m.ClassificationState) + i = encodeVarintGenerated(dAtA, i, uint64(len(m.ClassificationState))) + i-- + dAtA[i] = 0x12 + i -= len(m.Version) + copy(dAtA[i:], m.Version) + i = encodeVarintGenerated(dAtA, i, uint64(len(m.Version))) + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + func (m *ExposureClass) Marshal() (dAtA []byte, err error) { size := m.Size() dAtA = make([]byte, size) @@ -11594,6 +11828,46 @@ func (m *LastOperation) MarshalToSizedBuffer(dAtA []byte) (int, error) { return len(dAtA) - i, nil } +func (m *LifecycleStage) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *LifecycleStage) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *LifecycleStage) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.StartTime != nil { + { + size, err := m.StartTime.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintGenerated(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x12 + } + i -= len(m.Classification) + copy(dAtA[i:], m.Classification) + i = encodeVarintGenerated(dAtA, i, uint64(len(m.Classification))) + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + func (m *LoadBalancerServicesProxyProtocol) Marshal() (dAtA []byte, err error) { size := m.Size() dAtA = make([]byte, size) @@ -11857,6 +12131,48 @@ func (m *MachineImageVersion) MarshalToSizedBuffer(dAtA []byte) (int, error) { return len(dAtA) - i, nil } +func (m *MachineImageVersionStatus) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MachineImageVersionStatus) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MachineImageVersionStatus) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Versions) > 0 { + for iNdEx := len(m.Versions) - 1; iNdEx >= 0; iNdEx-- { + { + size, err := m.Versions[iNdEx].MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintGenerated(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x12 + } + } + i -= len(m.Name) + copy(dAtA[i:], m.Name) + i = encodeVarintGenerated(dAtA, i, uint64(len(m.Name))) + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + func (m *MachineType) Marshal() (dAtA []byte, err error) { size := m.Size() dAtA = make([]byte, size) @@ -17946,6 +18262,8 @@ func (m *CloudProfile) Size() (n int) { n += 1 + l + sovGenerated(uint64(l)) l = m.Spec.Size() n += 1 + l + sovGenerated(uint64(l)) + l = m.Status.Size() + n += 1 + l + sovGenerated(uint64(l)) return n } @@ -18032,6 +18350,27 @@ func (m *CloudProfileSpec) Size() (n int) { return n } +func (m *CloudProfileStatus) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if len(m.KubernetesVersions) > 0 { + for _, e := range m.KubernetesVersions { + l = e.Size() + n += 1 + l + sovGenerated(uint64(l)) + } + } + if len(m.MachineImageVersions) > 0 { + for _, e := range m.MachineImageVersions { + l = e.Size() + n += 1 + l + sovGenerated(uint64(l)) + } + } + return n +} + func (m *ClusterAutoscaler) Size() (n int) { if m == nil { return 0 @@ -18627,6 +18966,25 @@ func (m *ExpirableVersion) Size() (n int) { l = len(*m.Classification) n += 1 + l + sovGenerated(uint64(l)) } + if len(m.Lifecycle) > 0 { + for _, e := range m.Lifecycle { + l = e.Size() + n += 1 + l + sovGenerated(uint64(l)) + } + } + return n +} + +func (m *ExpirableVersionStatus) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.Version) + n += 1 + l + sovGenerated(uint64(l)) + l = len(m.ClassificationState) + n += 1 + l + sovGenerated(uint64(l)) return n } @@ -19459,6 +19817,21 @@ func (m *LastOperation) Size() (n int) { return n } +func (m *LifecycleStage) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.Classification) + n += 1 + l + sovGenerated(uint64(l)) + if m.StartTime != nil { + l = m.StartTime.Size() + n += 1 + l + sovGenerated(uint64(l)) + } + return n +} + func (m *LoadBalancerServicesProxyProtocol) Size() (n int) { if m == nil { return 0 @@ -19566,6 +19939,23 @@ func (m *MachineImageVersion) Size() (n int) { return n } +func (m *MachineImageVersionStatus) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.Name) + n += 1 + l + sovGenerated(uint64(l)) + if len(m.Versions) > 0 { + for _, e := range m.Versions { + l = e.Size() + n += 1 + l + sovGenerated(uint64(l)) + } + } + return n +} + func (m *MachineType) Size() (n int) { if m == nil { return 0 @@ -22001,6 +22391,7 @@ func (this *CloudProfile) String() string { s := strings.Join([]string{`&CloudProfile{`, `ObjectMeta:` + strings.Replace(strings.Replace(fmt.Sprintf("%v", this.ObjectMeta), "ObjectMeta", "v11.ObjectMeta", 1), `&`, ``, 1) + `,`, `Spec:` + strings.Replace(strings.Replace(this.Spec.String(), "CloudProfileSpec", "CloudProfileSpec", 1), `&`, ``, 1) + `,`, + `Status:` + strings.Replace(strings.Replace(this.Status.String(), "CloudProfileStatus", "CloudProfileStatus", 1), `&`, ``, 1) + `,`, `}`, }, "") return s @@ -22071,6 +22462,27 @@ func (this *CloudProfileSpec) String() string { }, "") return s } +func (this *CloudProfileStatus) String() string { + if this == nil { + return "nil" + } + repeatedStringForKubernetesVersions := "[]ExpirableVersionStatus{" + for _, f := range this.KubernetesVersions { + repeatedStringForKubernetesVersions += strings.Replace(strings.Replace(f.String(), "ExpirableVersionStatus", "ExpirableVersionStatus", 1), `&`, ``, 1) + "," + } + repeatedStringForKubernetesVersions += "}" + repeatedStringForMachineImageVersions := "[]MachineImageVersionStatus{" + for _, f := range this.MachineImageVersions { + repeatedStringForMachineImageVersions += strings.Replace(strings.Replace(f.String(), "MachineImageVersionStatus", "MachineImageVersionStatus", 1), `&`, ``, 1) + "," + } + repeatedStringForMachineImageVersions += "}" + s := strings.Join([]string{`&CloudProfileStatus{`, + `KubernetesVersions:` + repeatedStringForKubernetesVersions + `,`, + `MachineImageVersions:` + repeatedStringForMachineImageVersions + `,`, + `}`, + }, "") + return s +} func (this *ClusterAutoscaler) String() string { if this == nil { return "nil" @@ -22454,10 +22866,27 @@ func (this *ExpirableVersion) String() string { if this == nil { return "nil" } + repeatedStringForLifecycle := "[]LifecycleStage{" + for _, f := range this.Lifecycle { + repeatedStringForLifecycle += strings.Replace(strings.Replace(f.String(), "LifecycleStage", "LifecycleStage", 1), `&`, ``, 1) + "," + } + repeatedStringForLifecycle += "}" s := strings.Join([]string{`&ExpirableVersion{`, `Version:` + fmt.Sprintf("%v", this.Version) + `,`, `ExpirationDate:` + strings.Replace(fmt.Sprintf("%v", this.ExpirationDate), "Time", "v11.Time", 1) + `,`, `Classification:` + valueToStringGenerated(this.Classification) + `,`, + `Lifecycle:` + repeatedStringForLifecycle + `,`, + `}`, + }, "") + return s +} +func (this *ExpirableVersionStatus) String() string { + if this == nil { + return "nil" + } + s := strings.Join([]string{`&ExpirableVersionStatus{`, + `Version:` + fmt.Sprintf("%v", this.Version) + `,`, + `ClassificationState:` + fmt.Sprintf("%v", this.ClassificationState) + `,`, `}`, }, "") return s @@ -22990,6 +23419,17 @@ func (this *LastOperation) String() string { }, "") return s } +func (this *LifecycleStage) String() string { + if this == nil { + return "nil" + } + s := strings.Join([]string{`&LifecycleStage{`, + `Classification:` + fmt.Sprintf("%v", this.Classification) + `,`, + `StartTime:` + strings.Replace(fmt.Sprintf("%v", this.StartTime), "Time", "v11.Time", 1) + `,`, + `}`, + }, "") + return s +} func (this *LoadBalancerServicesProxyProtocol) String() string { if this == nil { return "nil" @@ -23061,6 +23501,22 @@ func (this *MachineImageVersion) String() string { }, "") return s } +func (this *MachineImageVersionStatus) String() string { + if this == nil { + return "nil" + } + repeatedStringForVersions := "[]ExpirableVersionStatus{" + for _, f := range this.Versions { + repeatedStringForVersions += strings.Replace(strings.Replace(f.String(), "ExpirableVersionStatus", "ExpirableVersionStatus", 1), `&`, ``, 1) + "," + } + repeatedStringForVersions += "}" + s := strings.Join([]string{`&MachineImageVersionStatus{`, + `Name:` + fmt.Sprintf("%v", this.Name) + `,`, + `Versions:` + repeatedStringForVersions + `,`, + `}`, + }, "") + return s +} func (this *MachineType) String() string { if this == nil { return "nil" @@ -28043,6 +28499,39 @@ func (m *CloudProfile) Unmarshal(dAtA []byte) error { return err } iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Status", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthGenerated + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthGenerated + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Status.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex default: iNdEx = preIndex skippy, err := skipGenerated(dAtA[iNdEx:]) @@ -28557,18 +29046,84 @@ func (m *CloudProfileSpec) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - if m.SeedSelector == nil { - m.SeedSelector = &SeedSelector{} - } - if err := m.SeedSelector.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + if m.SeedSelector == nil { + m.SeedSelector = &SeedSelector{} + } + if err := m.SeedSelector.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 8: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Type", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthGenerated + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthGenerated + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Type = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 9: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field VolumeTypes", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthGenerated + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthGenerated + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.VolumeTypes = append(m.VolumeTypes, VolumeType{}) + if err := m.VolumeTypes[len(m.VolumeTypes)-1].Unmarshal(dAtA[iNdEx:postIndex]); err != nil { return err } iNdEx = postIndex - case 8: + case 10: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Type", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field Bastion", wireType) } - var stringLen uint64 + var msglen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowGenerated @@ -28578,27 +29133,81 @@ func (m *CloudProfileSpec) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + msglen |= int(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { + if msglen < 0 { return ErrInvalidLengthGenerated } - postIndex := iNdEx + intStringLen + postIndex := iNdEx + msglen if postIndex < 0 { return ErrInvalidLengthGenerated } if postIndex > l { return io.ErrUnexpectedEOF } - m.Type = string(dAtA[iNdEx:postIndex]) + if m.Bastion == nil { + m.Bastion = &Bastion{} + } + if err := m.Bastion.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } iNdEx = postIndex - case 9: + default: + iNdEx = preIndex + skippy, err := skipGenerated(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthGenerated + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *CloudProfileStatus) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: CloudProfileStatus: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: CloudProfileStatus: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field VolumeTypes", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field KubernetesVersions", wireType) } var msglen int for shift := uint(0); ; shift += 7 { @@ -28625,14 +29234,14 @@ func (m *CloudProfileSpec) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - m.VolumeTypes = append(m.VolumeTypes, VolumeType{}) - if err := m.VolumeTypes[len(m.VolumeTypes)-1].Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + m.KubernetesVersions = append(m.KubernetesVersions, ExpirableVersionStatus{}) + if err := m.KubernetesVersions[len(m.KubernetesVersions)-1].Unmarshal(dAtA[iNdEx:postIndex]); err != nil { return err } iNdEx = postIndex - case 10: + case 2: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Bastion", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field MachineImageVersions", wireType) } var msglen int for shift := uint(0); ; shift += 7 { @@ -28659,10 +29268,8 @@ func (m *CloudProfileSpec) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - if m.Bastion == nil { - m.Bastion = &Bastion{} - } - if err := m.Bastion.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + m.MachineImageVersions = append(m.MachineImageVersions, MachineImageVersionStatus{}) + if err := m.MachineImageVersions[len(m.MachineImageVersions)-1].Unmarshal(dAtA[iNdEx:postIndex]); err != nil { return err } iNdEx = postIndex @@ -33063,43 +33670,192 @@ func (m *ExpirableVersion) Unmarshal(dAtA []byte) error { iNdEx = postIndex case 2: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ExpirationDate", wireType) - } - var msglen int - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowGenerated - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - msglen |= int(b&0x7F) << shift - if b < 0x80 { - break - } - } - if msglen < 0 { - return ErrInvalidLengthGenerated - } - postIndex := iNdEx + msglen - if postIndex < 0 { - return ErrInvalidLengthGenerated - } - if postIndex > l { - return io.ErrUnexpectedEOF - } - if m.ExpirationDate == nil { - m.ExpirationDate = &v11.Time{} - } - if err := m.ExpirationDate.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { - return err - } - iNdEx = postIndex - case 3: - if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Classification", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ExpirationDate", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthGenerated + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthGenerated + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if m.ExpirationDate == nil { + m.ExpirationDate = &v11.Time{} + } + if err := m.ExpirationDate.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Classification", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthGenerated + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthGenerated + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + s := VersionClassification(dAtA[iNdEx:postIndex]) + m.Classification = &s + iNdEx = postIndex + case 4: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Lifecycle", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthGenerated + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthGenerated + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Lifecycle = append(m.Lifecycle, LifecycleStage{}) + if err := m.Lifecycle[len(m.Lifecycle)-1].Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipGenerated(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthGenerated + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *ExpirableVersionStatus) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: ExpirableVersionStatus: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: ExpirableVersionStatus: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Version", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthGenerated + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthGenerated + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Version = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ClassificationState", wireType) } var stringLen uint64 for shift := uint(0); ; shift += 7 { @@ -33127,8 +33883,7 @@ func (m *ExpirableVersion) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - s := VersionClassification(dAtA[iNdEx:postIndex]) - m.Classification = &s + m.ClassificationState = VersionClassification(dAtA[iNdEx:postIndex]) iNdEx = postIndex default: iNdEx = preIndex @@ -39911,6 +40666,124 @@ func (m *LastOperation) Unmarshal(dAtA []byte) error { } return nil } +func (m *LifecycleStage) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: LifecycleStage: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: LifecycleStage: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Classification", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthGenerated + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthGenerated + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Classification = VersionClassification(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field StartTime", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthGenerated + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthGenerated + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if m.StartTime == nil { + m.StartTime = &v11.Time{} + } + if err := m.StartTime.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipGenerated(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthGenerated + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} func (m *LoadBalancerServicesProxyProtocol) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 @@ -40673,6 +41546,122 @@ func (m *MachineImageVersion) Unmarshal(dAtA []byte) error { } return nil } +func (m *MachineImageVersionStatus) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MachineImageVersionStatus: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MachineImageVersionStatus: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Name", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthGenerated + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthGenerated + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Name = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Versions", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenerated + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthGenerated + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthGenerated + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Versions = append(m.Versions, ExpirableVersionStatus{}) + if err := m.Versions[len(m.Versions)-1].Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipGenerated(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthGenerated + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} func (m *MachineType) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 diff --git a/pkg/apis/core/v1beta1/generated.proto b/pkg/apis/core/v1beta1/generated.proto index d56ba4bc2d2..304310c3cbd 100644 --- a/pkg/apis/core/v1beta1/generated.proto +++ b/pkg/apis/core/v1beta1/generated.proto @@ -346,6 +346,9 @@ message CloudProfile { // Spec defines the provider environment properties. // +optional optional CloudProfileSpec spec = 2; + + // Status contains the current status of the cloud profile. + optional CloudProfileStatus status = 3; } // CloudProfileList is a collection of CloudProfiles. @@ -418,6 +421,15 @@ message CloudProfileSpec { optional Bastion bastion = 10; } +// CloudProfileStatus contains the status of the cloud profile. +message CloudProfileStatus { + // KubernetesVersions contains the statuses of the kubernetes versions. + repeated ExpirableVersionStatus kubernetesVersions = 1; + + // MachineImageVersions contains the statuses of the machine image versions. + repeated MachineImageVersionStatus machineImageVersions = 2; +} + // ClusterAutoscaler contains the configuration flags for the Kubernetes cluster autoscaler. message ClusterAutoscaler { // ScaleDownDelayAfterAdd defines how long after scale up that scale down evaluation resumes (default: 1 hour). @@ -896,13 +908,27 @@ message ExpirableVersion { // Version is the version identifier. optional string version = 1; - // ExpirationDate defines the time at which this version expires. + // Deprecated: Is replaced by Lifecycle. // +optional optional .k8s.io.apimachinery.pkg.apis.meta.v1.Time expirationDate = 2; - // Classification defines the state of a version (preview, supported, deprecated) + // Classification defines the state of a version (preview, supported, deprecated). + // Deprecated: Is replaced by Lifecycle. // +optional optional string classification = 3; + + // Lifecycle defines the lifecycle stages for this version. Cannot be used in combination with Classification and ExpirationDate. + // +optional + repeated LifecycleStage lifecycle = 4; +} + +// ExpirableVersionStatus defines the current status of an expirable version. +message ExpirableVersionStatus { + // Version is the version identifier. + optional string version = 1; + + // ClassificationState reflects the current state in the classification lifecycle. + optional string classificationState = 2; } // ExposureClass represents a control plane endpoint exposure strategy. @@ -1677,6 +1703,15 @@ message LastOperation { optional string type = 5; } +message LifecycleStage { + // Classification is the category of this lifecycle stage (unavailable, preview, supported, deprecated, expired). + optional string classification = 1; + + // StartTime defines when this lifecycle stage becomes active. + // +optional + optional .k8s.io.apimachinery.pkg.apis.meta.v1.Time startTime = 2; +} + // LoadBalancerServicesProxyProtocol controls whether ProxyProtocol is (optionally) allowed for the load balancer services. message LoadBalancerServicesProxyProtocol { // Allowed controls whether the ProxyProtocol is optionally allowed for the load balancer services. @@ -1764,6 +1799,14 @@ message MachineImageVersion { optional string kubeletVersionConstraint = 4; } +message MachineImageVersionStatus { + // Name matches the name of the MachineImage the status is represented of. + optional string name = 1; + + // Versions contains the statuses of the machine image versions. + repeated ExpirableVersionStatus versions = 2; +} + // MachineType contains certain properties of a machine type. message MachineType { // CPU is the number of CPUs for this machine type. diff --git a/pkg/apis/core/v1beta1/helper/cloudprofile.go b/pkg/apis/core/v1beta1/helper/cloudprofile.go new file mode 100644 index 00000000000..a4e530b134d --- /dev/null +++ b/pkg/apis/core/v1beta1/helper/cloudprofile.go @@ -0,0 +1,75 @@ +package helper + +import ( + "time" + + "github.com/gardener/gardener/pkg/apis/core/v1beta1" +) + +func CurrentLifecycleClassification(version v1beta1.ExpirableVersion) v1beta1.VersionClassification { + var ( + currentClassification = v1beta1.ClassificationUnavailable + currentTime = time.Now() + ) + + if version.Classification != nil || version.ExpirationDate != nil { + // old cloud profile definition, convert to lifecycle + // this can be removed as soon as we remove the old classification and expiration date fields + + if version.Classification != nil { + version.Lifecycle = append(version.Lifecycle, v1beta1.LifecycleStage{ + Classification: *version.Classification, + }) + } + + if version.ExpirationDate != nil { + if version.Classification == nil { + version.Lifecycle = append(version.Lifecycle, v1beta1.LifecycleStage{ + Classification: v1beta1.ClassificationSupported, + }) + } + + version.Lifecycle = append(version.Lifecycle, v1beta1.LifecycleStage{ + Classification: v1beta1.ClassificationExpired, + StartTime: version.ExpirationDate, + }) + } + } + + if len(version.Lifecycle) == 0 { + // when there is no classification lifecycle defined then default to supported + version.Lifecycle = append(version.Lifecycle, v1beta1.LifecycleStage{ + Classification: v1beta1.ClassificationSupported, + }) + } + + for _, stage := range version.Lifecycle { + startTime := time.Time{} + if stage.StartTime != nil { + startTime = stage.StartTime.Time + } + + if startTime.Before(currentTime) { + currentClassification = stage.Classification + } + } + + return currentClassification +} + +func VersionIsExpired(version v1beta1.ExpirableVersion) bool { + return CurrentLifecycleClassification(version) == v1beta1.ClassificationExpired +} + +func VersionIsActive(version v1beta1.ExpirableVersion) bool { + curr := CurrentLifecycleClassification(version) + return curr != v1beta1.ClassificationExpired && curr != v1beta1.ClassificationUnavailable +} + +func VersionIsSupported(version v1beta1.ExpirableVersion) bool { + return CurrentLifecycleClassification(version) == v1beta1.ClassificationSupported +} + +func VersionIsPreview(version v1beta1.ExpirableVersion) bool { + return CurrentLifecycleClassification(version) == v1beta1.ClassificationPreview +} diff --git a/pkg/apis/core/v1beta1/helper/cloudprofile_test.go b/pkg/apis/core/v1beta1/helper/cloudprofile_test.go new file mode 100644 index 00000000000..1222490c4d4 --- /dev/null +++ b/pkg/apis/core/v1beta1/helper/cloudprofile_test.go @@ -0,0 +1,154 @@ +package helper_test + +import ( + "time" + + . "github.com/onsi/ginkgo/v2" + . "github.com/onsi/gomega" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/utils/ptr" + + gardencorev1beta1 "github.com/gardener/gardener/pkg/apis/core/v1beta1" + "github.com/gardener/gardener/pkg/apis/core/v1beta1/helper" +) + +var _ = Describe("CloudProfile Helper", func() { + var ( + now = time.Now() + ) + + Context("calculate the current lifecycle classification", func() { + It("only version is given", func() { + classification := helper.CurrentLifecycleClassification(gardencorev1beta1.ExpirableVersion{ + Version: "1.28.0", + }) + Expect(classification).To(Equal(gardencorev1beta1.ClassificationSupported)) + }) + + It("unavailable classification due to scheduled lifecycle start in the future", func() { + classification := helper.CurrentLifecycleClassification(gardencorev1beta1.ExpirableVersion{ + Version: "1.28.0", + Lifecycle: []gardencorev1beta1.LifecycleStage{ + { + Classification: gardencorev1beta1.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(3 * time.Hour))), + }, + }, + }) + Expect(classification).To(Equal(gardencorev1beta1.ClassificationUnavailable)) + }) + + It("version is in preview stage", func() { + classification := helper.CurrentLifecycleClassification(gardencorev1beta1.ExpirableVersion{ + Version: "1.28.0", + Lifecycle: []gardencorev1beta1.LifecycleStage{ + { + Classification: gardencorev1beta1.ClassificationPreview, + StartTime: ptr.To(metav1.NewTime(now.Add(-1 * time.Hour))), + }, + { + Classification: gardencorev1beta1.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(3 * time.Hour))), + }, + }, + }) + Expect(classification).To(Equal(gardencorev1beta1.ClassificationPreview)) + }) + + It("full version lifecycle with version currently in supported stage", func() { + classification := helper.CurrentLifecycleClassification(gardencorev1beta1.ExpirableVersion{ + Version: "1.28.0", + Lifecycle: []gardencorev1beta1.LifecycleStage{ + { + Classification: gardencorev1beta1.ClassificationPreview, + StartTime: ptr.To(metav1.NewTime(now.Add(-3 * time.Hour))), + }, + { + Classification: gardencorev1beta1.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(-1 * time.Hour))), + }, + { + Classification: gardencorev1beta1.ClassificationDeprecated, + StartTime: ptr.To(metav1.NewTime(now.Add(5 * time.Hour))), + }, + { + Classification: gardencorev1beta1.ClassificationExpired, + StartTime: ptr.To(metav1.NewTime(now.Add(8 * time.Hour))), + }, + }, + }) + Expect(classification).To(Equal(gardencorev1beta1.ClassificationSupported)) + }) + + It("version is expired", func() { + classification := helper.CurrentLifecycleClassification(gardencorev1beta1.ExpirableVersion{ + Version: "1.28.0", + Lifecycle: []gardencorev1beta1.LifecycleStage{ + { + Classification: gardencorev1beta1.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(-4 * time.Hour))), + }, + { + Classification: gardencorev1beta1.ClassificationDeprecated, + StartTime: ptr.To(metav1.NewTime(now.Add(-3 * time.Hour))), + }, + { + Classification: gardencorev1beta1.ClassificationExpired, + StartTime: ptr.To(metav1.NewTime(now.Add(-1 * time.Hour))), + }, + }, + }) + Expect(classification).To(Equal(gardencorev1beta1.ClassificationExpired)) + }) + + It("first lifecycle start time field is optional", func() { + classification := helper.CurrentLifecycleClassification(gardencorev1beta1.ExpirableVersion{ + Version: "1.28.5", + Lifecycle: []gardencorev1beta1.LifecycleStage{ + { + Classification: gardencorev1beta1.ClassificationPreview, + }, + { + Classification: gardencorev1beta1.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(3 * time.Hour))), + }, + { + Classification: gardencorev1beta1.ClassificationDeprecated, + StartTime: ptr.To(metav1.NewTime(now.Add(4 * time.Hour))), + }, + { + Classification: gardencorev1beta1.ClassificationExpired, + StartTime: ptr.To(metav1.NewTime(now.Add(5 * time.Hour))), + }, + }, + }) + Expect(classification).To(Equal(gardencorev1beta1.ClassificationPreview)) + }) + + It("determining supported for deprecated classification field", func() { + classification := helper.CurrentLifecycleClassification(gardencorev1beta1.ExpirableVersion{ + Classification: ptr.To(gardencorev1beta1.ClassificationSupported), + Version: "1.28.0", + }) + Expect(classification).To(Equal(gardencorev1beta1.ClassificationSupported)) + }) + + It("determining expired for deprecated expiration date field", func() { + classification := helper.CurrentLifecycleClassification(gardencorev1beta1.ExpirableVersion{ + ExpirationDate: ptr.To(metav1.NewTime(now.Add(-1 * time.Hour))), + Version: "1.28.0", + }) + Expect(classification).To(Equal(gardencorev1beta1.ClassificationExpired)) + }) + + It("determining preview for deprecated classification and expiration date field", func() { + classification := helper.CurrentLifecycleClassification(gardencorev1beta1.ExpirableVersion{ + Classification: ptr.To(gardencorev1beta1.ClassificationPreview), + Version: "1.28.0", + ExpirationDate: ptr.To(metav1.NewTime(now.Add(3 * time.Hour))), + }) + Expect(classification).To(Equal(gardencorev1beta1.ClassificationPreview)) + }) + + }) +}) diff --git a/pkg/apis/core/v1beta1/types_cloudprofile.go b/pkg/apis/core/v1beta1/types_cloudprofile.go index 90858fbbcb6..5a4fa3094cb 100644 --- a/pkg/apis/core/v1beta1/types_cloudprofile.go +++ b/pkg/apis/core/v1beta1/types_cloudprofile.go @@ -23,6 +23,8 @@ type CloudProfile struct { // Spec defines the provider environment properties. // +optional Spec CloudProfileSpec `json:"spec,omitempty" protobuf:"bytes,2,opt,name=spec"` + // Status contains the current status of the cloud profile. + Status CloudProfileStatus `json:"status,omitempty" protobuf:"bytes,3,opt,name=status"` } // +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object @@ -136,12 +138,24 @@ type MachineImageVersion struct { type ExpirableVersion struct { // Version is the version identifier. Version string `json:"version" protobuf:"bytes,1,opt,name=version"` - // ExpirationDate defines the time at which this version expires. + // Deprecated: Is replaced by Lifecycle. // +optional ExpirationDate *metav1.Time `json:"expirationDate,omitempty" protobuf:"bytes,2,opt,name=expirationDate"` - // Classification defines the state of a version (preview, supported, deprecated) + // Classification defines the state of a version (preview, supported, deprecated). + // Deprecated: Is replaced by Lifecycle. // +optional Classification *VersionClassification `json:"classification,omitempty" protobuf:"bytes,3,opt,name=classification,casttype=VersionClassification"` + // Lifecycle defines the lifecycle stages for this version. Cannot be used in combination with Classification and ExpirationDate. + // +optional + Lifecycle []LifecycleStage `json:"lifecycle,omitempty" protobuf:"bytes,4,opt,name=lifecycle"` +} + +type LifecycleStage struct { + // Classification is the category of this lifecycle stage (unavailable, preview, supported, deprecated, expired). + Classification VersionClassification `json:"classification" protobuf:"bytes,1,opt,name=classification,casttype=VersionClassification"` + // StartTime defines when this lifecycle stage becomes active. + // +optional + StartTime *metav1.Time `json:"startTime,omitempty" protobuf:"bytes,2,opt,name=startTime"` } // MachineType contains certain properties of a machine type. @@ -250,6 +264,29 @@ type BastionMachineType struct { Name string `json:"name" protobuf:"bytes,1,name=name"` } +// CloudProfileStatus contains the status of the cloud profile. +type CloudProfileStatus struct { + // KubernetesVersions contains the statuses of the kubernetes versions. + KubernetesVersions []ExpirableVersionStatus `json:"kubernetesVersions,omitempty" protobuf:"bytes,1,name=kubernetesVersions"` + // MachineImageVersions contains the statuses of the machine image versions. + MachineImageVersions []MachineImageVersionStatus `json:"machineImageVersions,omitempty" protobuf:"bytes,2,name=machineImageVersions"` +} + +type MachineImageVersionStatus struct { + // Name matches the name of the MachineImage the status is represented of. + Name string `json:"name,omitempty" protobuf:"bytes,1,name=name"` + // Versions contains the statuses of the machine image versions. + Versions []ExpirableVersionStatus `json:"versions,omitempty" protobuf:"bytes,2,name=versions"` +} + +// ExpirableVersionStatus defines the current status of an expirable version. +type ExpirableVersionStatus struct { + // Version is the version identifier. + Version string `json:"version" protobuf:"bytes,1,opt,name=version"` + // ClassificationState reflects the current state in the classification lifecycle. + ClassificationState VersionClassification `json:"classificationState,omitempty" protobuf:"bytes,2,opt,name=classificationState,casttype=VersionClassification"` +} + const ( // VolumeClassStandard is a constant for the standard volume class. VolumeClassStandard string = "standard" @@ -261,6 +298,8 @@ const ( type VersionClassification string const ( + // ClassificationUnavailable indicates that a version is currently not available and is planned to become available depending on the classification lifecycle. + ClassificationUnavailable VersionClassification = "unavailable" // ClassificationPreview indicates that a version has recently been added and not promoted to "Supported" yet. // ClassificationPreview versions will not be considered for automatic Kubernetes and Machine Image patch version updates. ClassificationPreview VersionClassification = "preview" @@ -271,6 +310,9 @@ const ( // ClassificationDeprecated indicates that a patch version should not be used anymore, should be updated to a new version // and will eventually expire. ClassificationDeprecated VersionClassification = "deprecated" + // ClassificationExpired indicates that a version has expired. + // New entities with that version cannot be created and existing entities are forcefully migrated to a higher version during the maintenance time. + ClassificationExpired VersionClassification = "expired" ) // MachineImageUpdateStrategy is the update strategy to use for a machine image diff --git a/pkg/apis/core/v1beta1/zz_generated.conversion.go b/pkg/apis/core/v1beta1/zz_generated.conversion.go index 0933c58705b..5077d6f44a0 100644 --- a/pkg/apis/core/v1beta1/zz_generated.conversion.go +++ b/pkg/apis/core/v1beta1/zz_generated.conversion.go @@ -331,6 +331,16 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } + if err := s.AddGeneratedConversionFunc((*CloudProfileStatus)(nil), (*core.CloudProfileStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_CloudProfileStatus_To_core_CloudProfileStatus(a.(*CloudProfileStatus), b.(*core.CloudProfileStatus), scope) + }); err != nil { + return err + } + if err := s.AddGeneratedConversionFunc((*core.CloudProfileStatus)(nil), (*CloudProfileStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_core_CloudProfileStatus_To_v1beta1_CloudProfileStatus(a.(*core.CloudProfileStatus), b.(*CloudProfileStatus), scope) + }); err != nil { + return err + } if err := s.AddGeneratedConversionFunc((*ClusterAutoscaler)(nil), (*core.ClusterAutoscaler)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1beta1_ClusterAutoscaler_To_core_ClusterAutoscaler(a.(*ClusterAutoscaler), b.(*core.ClusterAutoscaler), scope) }); err != nil { @@ -611,6 +621,16 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } + if err := s.AddGeneratedConversionFunc((*ExpirableVersionStatus)(nil), (*core.ExpirableVersionStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_ExpirableVersionStatus_To_core_ExpirableVersionStatus(a.(*ExpirableVersionStatus), b.(*core.ExpirableVersionStatus), scope) + }); err != nil { + return err + } + if err := s.AddGeneratedConversionFunc((*core.ExpirableVersionStatus)(nil), (*ExpirableVersionStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_core_ExpirableVersionStatus_To_v1beta1_ExpirableVersionStatus(a.(*core.ExpirableVersionStatus), b.(*ExpirableVersionStatus), scope) + }); err != nil { + return err + } if err := s.AddGeneratedConversionFunc((*ExposureClass)(nil), (*core.ExposureClass)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1beta1_ExposureClass_To_core_ExposureClass(a.(*ExposureClass), b.(*core.ExposureClass), scope) }); err != nil { @@ -926,6 +946,16 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } + if err := s.AddGeneratedConversionFunc((*LifecycleStage)(nil), (*core.LifecycleStage)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_LifecycleStage_To_core_LifecycleStage(a.(*LifecycleStage), b.(*core.LifecycleStage), scope) + }); err != nil { + return err + } + if err := s.AddGeneratedConversionFunc((*core.LifecycleStage)(nil), (*LifecycleStage)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_core_LifecycleStage_To_v1beta1_LifecycleStage(a.(*core.LifecycleStage), b.(*LifecycleStage), scope) + }); err != nil { + return err + } if err := s.AddGeneratedConversionFunc((*LoadBalancerServicesProxyProtocol)(nil), (*core.LoadBalancerServicesProxyProtocol)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1beta1_LoadBalancerServicesProxyProtocol_To_core_LoadBalancerServicesProxyProtocol(a.(*LoadBalancerServicesProxyProtocol), b.(*core.LoadBalancerServicesProxyProtocol), scope) }); err != nil { @@ -976,6 +1006,16 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } + if err := s.AddGeneratedConversionFunc((*MachineImageVersionStatus)(nil), (*core.MachineImageVersionStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_MachineImageVersionStatus_To_core_MachineImageVersionStatus(a.(*MachineImageVersionStatus), b.(*core.MachineImageVersionStatus), scope) + }); err != nil { + return err + } + if err := s.AddGeneratedConversionFunc((*core.MachineImageVersionStatus)(nil), (*MachineImageVersionStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_core_MachineImageVersionStatus_To_v1beta1_MachineImageVersionStatus(a.(*core.MachineImageVersionStatus), b.(*MachineImageVersionStatus), scope) + }); err != nil { + return err + } if err := s.AddGeneratedConversionFunc((*MachineType)(nil), (*core.MachineType)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1beta1_MachineType_To_core_MachineType(a.(*MachineType), b.(*core.MachineType), scope) }); err != nil { @@ -2535,6 +2575,9 @@ func autoConvert_v1beta1_CloudProfile_To_core_CloudProfile(in *CloudProfile, out if err := Convert_v1beta1_CloudProfileSpec_To_core_CloudProfileSpec(&in.Spec, &out.Spec, s); err != nil { return err } + if err := Convert_v1beta1_CloudProfileStatus_To_core_CloudProfileStatus(&in.Status, &out.Status, s); err != nil { + return err + } return nil } @@ -2548,6 +2591,9 @@ func autoConvert_core_CloudProfile_To_v1beta1_CloudProfile(in *core.CloudProfile if err := Convert_core_CloudProfileSpec_To_v1beta1_CloudProfileSpec(&in.Spec, &out.Spec, s); err != nil { return err } + if err := Convert_core_CloudProfileStatus_To_v1beta1_CloudProfileStatus(&in.Status, &out.Status, s); err != nil { + return err + } return nil } @@ -2642,6 +2688,28 @@ func Convert_core_CloudProfileSpec_To_v1beta1_CloudProfileSpec(in *core.CloudPro return autoConvert_core_CloudProfileSpec_To_v1beta1_CloudProfileSpec(in, out, s) } +func autoConvert_v1beta1_CloudProfileStatus_To_core_CloudProfileStatus(in *CloudProfileStatus, out *core.CloudProfileStatus, s conversion.Scope) error { + out.KubernetesVersions = *(*[]core.ExpirableVersionStatus)(unsafe.Pointer(&in.KubernetesVersions)) + out.MachineImageVersions = *(*[]core.MachineImageVersionStatus)(unsafe.Pointer(&in.MachineImageVersions)) + return nil +} + +// Convert_v1beta1_CloudProfileStatus_To_core_CloudProfileStatus is an autogenerated conversion function. +func Convert_v1beta1_CloudProfileStatus_To_core_CloudProfileStatus(in *CloudProfileStatus, out *core.CloudProfileStatus, s conversion.Scope) error { + return autoConvert_v1beta1_CloudProfileStatus_To_core_CloudProfileStatus(in, out, s) +} + +func autoConvert_core_CloudProfileStatus_To_v1beta1_CloudProfileStatus(in *core.CloudProfileStatus, out *CloudProfileStatus, s conversion.Scope) error { + out.KubernetesVersions = *(*[]ExpirableVersionStatus)(unsafe.Pointer(&in.KubernetesVersions)) + out.MachineImageVersions = *(*[]MachineImageVersionStatus)(unsafe.Pointer(&in.MachineImageVersions)) + return nil +} + +// Convert_core_CloudProfileStatus_To_v1beta1_CloudProfileStatus is an autogenerated conversion function. +func Convert_core_CloudProfileStatus_To_v1beta1_CloudProfileStatus(in *core.CloudProfileStatus, out *CloudProfileStatus, s conversion.Scope) error { + return autoConvert_core_CloudProfileStatus_To_v1beta1_CloudProfileStatus(in, out, s) +} + func autoConvert_v1beta1_ClusterAutoscaler_To_core_ClusterAutoscaler(in *ClusterAutoscaler, out *core.ClusterAutoscaler, s conversion.Scope) error { out.ScaleDownDelayAfterAdd = (*metav1.Duration)(unsafe.Pointer(in.ScaleDownDelayAfterAdd)) out.ScaleDownDelayAfterDelete = (*metav1.Duration)(unsafe.Pointer(in.ScaleDownDelayAfterDelete)) @@ -3361,6 +3429,7 @@ func autoConvert_v1beta1_ExpirableVersion_To_core_ExpirableVersion(in *Expirable out.Version = in.Version out.ExpirationDate = (*metav1.Time)(unsafe.Pointer(in.ExpirationDate)) out.Classification = (*core.VersionClassification)(unsafe.Pointer(in.Classification)) + out.Lifecycle = *(*[]core.LifecycleStage)(unsafe.Pointer(&in.Lifecycle)) return nil } @@ -3373,6 +3442,7 @@ func autoConvert_core_ExpirableVersion_To_v1beta1_ExpirableVersion(in *core.Expi out.Version = in.Version out.ExpirationDate = (*metav1.Time)(unsafe.Pointer(in.ExpirationDate)) out.Classification = (*VersionClassification)(unsafe.Pointer(in.Classification)) + out.Lifecycle = *(*[]LifecycleStage)(unsafe.Pointer(&in.Lifecycle)) return nil } @@ -3381,6 +3451,28 @@ func Convert_core_ExpirableVersion_To_v1beta1_ExpirableVersion(in *core.Expirabl return autoConvert_core_ExpirableVersion_To_v1beta1_ExpirableVersion(in, out, s) } +func autoConvert_v1beta1_ExpirableVersionStatus_To_core_ExpirableVersionStatus(in *ExpirableVersionStatus, out *core.ExpirableVersionStatus, s conversion.Scope) error { + out.Version = in.Version + out.ClassificationState = core.VersionClassification(in.ClassificationState) + return nil +} + +// Convert_v1beta1_ExpirableVersionStatus_To_core_ExpirableVersionStatus is an autogenerated conversion function. +func Convert_v1beta1_ExpirableVersionStatus_To_core_ExpirableVersionStatus(in *ExpirableVersionStatus, out *core.ExpirableVersionStatus, s conversion.Scope) error { + return autoConvert_v1beta1_ExpirableVersionStatus_To_core_ExpirableVersionStatus(in, out, s) +} + +func autoConvert_core_ExpirableVersionStatus_To_v1beta1_ExpirableVersionStatus(in *core.ExpirableVersionStatus, out *ExpirableVersionStatus, s conversion.Scope) error { + out.Version = in.Version + out.ClassificationState = VersionClassification(in.ClassificationState) + return nil +} + +// Convert_core_ExpirableVersionStatus_To_v1beta1_ExpirableVersionStatus is an autogenerated conversion function. +func Convert_core_ExpirableVersionStatus_To_v1beta1_ExpirableVersionStatus(in *core.ExpirableVersionStatus, out *ExpirableVersionStatus, s conversion.Scope) error { + return autoConvert_core_ExpirableVersionStatus_To_v1beta1_ExpirableVersionStatus(in, out, s) +} + func autoConvert_v1beta1_ExposureClass_To_core_ExposureClass(in *ExposureClass, out *core.ExposureClass, s conversion.Scope) error { out.ObjectMeta = in.ObjectMeta out.Handler = in.Handler @@ -4371,6 +4463,28 @@ func Convert_core_LastOperation_To_v1beta1_LastOperation(in *core.LastOperation, return autoConvert_core_LastOperation_To_v1beta1_LastOperation(in, out, s) } +func autoConvert_v1beta1_LifecycleStage_To_core_LifecycleStage(in *LifecycleStage, out *core.LifecycleStage, s conversion.Scope) error { + out.Classification = core.VersionClassification(in.Classification) + out.StartTime = (*metav1.Time)(unsafe.Pointer(in.StartTime)) + return nil +} + +// Convert_v1beta1_LifecycleStage_To_core_LifecycleStage is an autogenerated conversion function. +func Convert_v1beta1_LifecycleStage_To_core_LifecycleStage(in *LifecycleStage, out *core.LifecycleStage, s conversion.Scope) error { + return autoConvert_v1beta1_LifecycleStage_To_core_LifecycleStage(in, out, s) +} + +func autoConvert_core_LifecycleStage_To_v1beta1_LifecycleStage(in *core.LifecycleStage, out *LifecycleStage, s conversion.Scope) error { + out.Classification = VersionClassification(in.Classification) + out.StartTime = (*metav1.Time)(unsafe.Pointer(in.StartTime)) + return nil +} + +// Convert_core_LifecycleStage_To_v1beta1_LifecycleStage is an autogenerated conversion function. +func Convert_core_LifecycleStage_To_v1beta1_LifecycleStage(in *core.LifecycleStage, out *LifecycleStage, s conversion.Scope) error { + return autoConvert_core_LifecycleStage_To_v1beta1_LifecycleStage(in, out, s) +} + func autoConvert_v1beta1_LoadBalancerServicesProxyProtocol_To_core_LoadBalancerServicesProxyProtocol(in *LoadBalancerServicesProxyProtocol, out *core.LoadBalancerServicesProxyProtocol, s conversion.Scope) error { out.Allowed = in.Allowed return nil @@ -4513,6 +4627,28 @@ func Convert_core_MachineImageVersion_To_v1beta1_MachineImageVersion(in *core.Ma return autoConvert_core_MachineImageVersion_To_v1beta1_MachineImageVersion(in, out, s) } +func autoConvert_v1beta1_MachineImageVersionStatus_To_core_MachineImageVersionStatus(in *MachineImageVersionStatus, out *core.MachineImageVersionStatus, s conversion.Scope) error { + out.Name = in.Name + out.Versions = *(*[]core.ExpirableVersionStatus)(unsafe.Pointer(&in.Versions)) + return nil +} + +// Convert_v1beta1_MachineImageVersionStatus_To_core_MachineImageVersionStatus is an autogenerated conversion function. +func Convert_v1beta1_MachineImageVersionStatus_To_core_MachineImageVersionStatus(in *MachineImageVersionStatus, out *core.MachineImageVersionStatus, s conversion.Scope) error { + return autoConvert_v1beta1_MachineImageVersionStatus_To_core_MachineImageVersionStatus(in, out, s) +} + +func autoConvert_core_MachineImageVersionStatus_To_v1beta1_MachineImageVersionStatus(in *core.MachineImageVersionStatus, out *MachineImageVersionStatus, s conversion.Scope) error { + out.Name = in.Name + out.Versions = *(*[]ExpirableVersionStatus)(unsafe.Pointer(&in.Versions)) + return nil +} + +// Convert_core_MachineImageVersionStatus_To_v1beta1_MachineImageVersionStatus is an autogenerated conversion function. +func Convert_core_MachineImageVersionStatus_To_v1beta1_MachineImageVersionStatus(in *core.MachineImageVersionStatus, out *MachineImageVersionStatus, s conversion.Scope) error { + return autoConvert_core_MachineImageVersionStatus_To_v1beta1_MachineImageVersionStatus(in, out, s) +} + func autoConvert_v1beta1_MachineType_To_core_MachineType(in *MachineType, out *core.MachineType, s conversion.Scope) error { out.CPU = in.CPU out.GPU = in.GPU diff --git a/pkg/apis/core/v1beta1/zz_generated.deepcopy.go b/pkg/apis/core/v1beta1/zz_generated.deepcopy.go index 1c8846e8629..a2d50e7ccd2 100644 --- a/pkg/apis/core/v1beta1/zz_generated.deepcopy.go +++ b/pkg/apis/core/v1beta1/zz_generated.deepcopy.go @@ -670,6 +670,7 @@ func (in *CloudProfile) DeepCopyInto(out *CloudProfile) { out.TypeMeta = in.TypeMeta in.ObjectMeta.DeepCopyInto(&out.ObjectMeta) in.Spec.DeepCopyInto(&out.Spec) + in.Status.DeepCopyInto(&out.Status) return } @@ -805,6 +806,34 @@ func (in *CloudProfileSpec) DeepCopy() *CloudProfileSpec { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *CloudProfileStatus) DeepCopyInto(out *CloudProfileStatus) { + *out = *in + if in.KubernetesVersions != nil { + in, out := &in.KubernetesVersions, &out.KubernetesVersions + *out = make([]ExpirableVersionStatus, len(*in)) + copy(*out, *in) + } + if in.MachineImageVersions != nil { + in, out := &in.MachineImageVersions, &out.MachineImageVersions + *out = make([]MachineImageVersionStatus, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CloudProfileStatus. +func (in *CloudProfileStatus) DeepCopy() *CloudProfileStatus { + if in == nil { + return nil + } + out := new(CloudProfileStatus) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ClusterAutoscaler) DeepCopyInto(out *ClusterAutoscaler) { *out = *in @@ -1657,6 +1686,13 @@ func (in *ExpirableVersion) DeepCopyInto(out *ExpirableVersion) { *out = new(VersionClassification) **out = **in } + if in.Lifecycle != nil { + in, out := &in.Lifecycle, &out.Lifecycle + *out = make([]LifecycleStage, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } return } @@ -1670,6 +1706,22 @@ func (in *ExpirableVersion) DeepCopy() *ExpirableVersion { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ExpirableVersionStatus) DeepCopyInto(out *ExpirableVersionStatus) { + *out = *in + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ExpirableVersionStatus. +func (in *ExpirableVersionStatus) DeepCopy() *ExpirableVersionStatus { + if in == nil { + return nil + } + out := new(ExpirableVersionStatus) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ExposureClass) DeepCopyInto(out *ExposureClass) { *out = *in @@ -2833,6 +2885,26 @@ func (in *LastOperation) DeepCopy() *LastOperation { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *LifecycleStage) DeepCopyInto(out *LifecycleStage) { + *out = *in + if in.StartTime != nil { + in, out := &in.StartTime, &out.StartTime + *out = (*in).DeepCopy() + } + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new LifecycleStage. +func (in *LifecycleStage) DeepCopy() *LifecycleStage { + if in == nil { + return nil + } + out := new(LifecycleStage) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *LoadBalancerServicesProxyProtocol) DeepCopyInto(out *LoadBalancerServicesProxyProtocol) { *out = *in @@ -2978,6 +3050,27 @@ func (in *MachineImageVersion) DeepCopy() *MachineImageVersion { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *MachineImageVersionStatus) DeepCopyInto(out *MachineImageVersionStatus) { + *out = *in + if in.Versions != nil { + in, out := &in.Versions, &out.Versions + *out = make([]ExpirableVersionStatus, len(*in)) + copy(*out, *in) + } + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new MachineImageVersionStatus. +func (in *MachineImageVersionStatus) DeepCopy() *MachineImageVersionStatus { + if in == nil { + return nil + } + out := new(MachineImageVersionStatus) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *MachineType) DeepCopyInto(out *MachineType) { *out = *in diff --git a/pkg/apis/core/validation/cloudprofile.go b/pkg/apis/core/validation/cloudprofile.go index f5be475eee4..5bcaf22aad0 100644 --- a/pkg/apis/core/validation/cloudprofile.go +++ b/pkg/apis/core/validation/cloudprofile.go @@ -50,9 +50,60 @@ func ValidateCloudProfileUpdate(newProfile, oldProfile *core.CloudProfile) field } // ValidateCloudProfileSpecUpdate validates the spec update of a CloudProfile -func ValidateCloudProfileSpecUpdate(_, _ *core.CloudProfileSpec, _ *field.Path) field.ErrorList { +func ValidateCloudProfileSpecUpdate(new, old *core.CloudProfileSpec, fldPath *field.Path) field.ErrorList { allErrs := field.ErrorList{} + allErrs = append(allErrs, ValidateCloudProfileExpirableVersionsUpdate(new.Kubernetes.Versions, old.Kubernetes.Versions, fldPath.Child("kubernetes").Child("versions"))...) + + oldMachineImageVersions := map[string]core.MachineImage{} + for _, version := range old.MachineImages { + oldMachineImageVersions[version.Name] = version + } + + for i, newMachineImage := range new.MachineImages { + oldMachineImage, ok := oldMachineImageVersions[newMachineImage.Name] + if !ok { + continue + } + + var ( + oldVersions, newVersions []core.ExpirableVersion + ) + + for _, oldVersion := range oldMachineImage.Versions { + oldVersions = append(oldVersions, oldVersion.ExpirableVersion) + } + for _, newVersion := range newMachineImage.Versions { + newVersions = append(newVersions, newVersion.ExpirableVersion) + } + + allErrs = append(allErrs, ValidateCloudProfileExpirableVersionsUpdate(newVersions, oldVersions, fldPath.Child("machineImages").Index(i).Child("versions"))...) + } + + return allErrs +} + +// ValidateCloudProfileExpirableVersionsUpdate validates the expirable versions update of a CloudProfile expirable version +func ValidateCloudProfileExpirableVersionsUpdate(new, old []core.ExpirableVersion, fldPath *field.Path) field.ErrorList { + allErrs := field.ErrorList{} + + oldVersions := map[string]core.ExpirableVersion{} + for _, version := range old { + oldVersions[version.Version] = version + } + + for i, newVersion := range new { + oldVersion, ok := oldVersions[newVersion.Version] + if !ok { + continue + } + + if helper.CurrentLifecycleClassification(oldVersion) != core.ClassificationUnavailable && + helper.CurrentLifecycleClassification(newVersion) == core.ClassificationUnavailable { + allErrs = append(allErrs, field.Forbidden(fldPath.Index(i), "a version cannot be turned into unavailable if it already was already moved into a later lifecycle stage")) + } + } + return allErrs } @@ -84,6 +135,17 @@ func ValidateCloudProfileSpec(spec *core.CloudProfileSpec, fldPath *field.Path) return allErrs } +func validateCloudProfileKubernetesClassificationLifecycleStartTimesOrder(kubernetes *core.KubernetesSettings, fldPath *field.Path) field.ErrorList { + allErrs := field.ErrorList{} + if kubernetes == nil { + return allErrs + } + for i, version := range kubernetes.Versions { + allErrs = append(allErrs, validateLifecycleStartTimes(version.Lifecycle, fldPath.Child("versions").Index(i))...) + } + return allErrs +} + func validateCloudProfileKubernetesSettings(kubernetes core.KubernetesSettings, fldPath *field.Path) field.ErrorList { allErrs := field.ErrorList{} if len(kubernetes.Versions) == 0 { @@ -97,6 +159,12 @@ func validateCloudProfileKubernetesSettings(kubernetes core.KubernetesSettings, allErrs = append(allErrs, field.Invalid(fldPath.Child("versions[]").Child("expirationDate"), latestKubernetesVersion.ExpirationDate, fmt.Sprintf("expiration date of latest kubernetes version ('%s') must not be set", latestKubernetesVersion.Version))) } + if len(latestKubernetesVersion.Lifecycle) > 0 { + if latestKubernetesVersion.Lifecycle[len(latestKubernetesVersion.Lifecycle)-1].Classification == core.ClassificationExpired { + allErrs = append(allErrs, field.Invalid(fldPath.Child("versions[]").Child("lifecycle"), latestKubernetesVersion.ExpirationDate, fmt.Sprintf("expiration date of latest kubernetes version ('%s') must not be set", latestKubernetesVersion.Version))) + } + } + allErrs = append(allErrs, validateKubernetesVersions(kubernetes.Versions, fldPath)...) for i, version := range kubernetes.Versions { @@ -110,7 +178,7 @@ func validateCloudProfileKubernetesSettings(kubernetes core.KubernetesSettings, func validateSupportedVersionsConfiguration(version core.ExpirableVersion, allVersions []core.ExpirableVersion, fldPath *field.Path) field.ErrorList { allErrs := field.ErrorList{} - if version.Classification != nil && *version.Classification == core.ClassificationSupported { + if helper.VersionIsSupported(version) { currentSemVer, err := semver.NewVersion(version.Version) if err != nil { // check is already performed by caller, avoid duplicate error @@ -123,15 +191,51 @@ func validateSupportedVersionsConfiguration(version core.ExpirableVersion, allVe return allErrs } - // do not allow adding multiple supported versions per minor version + // do not allow adding multiple overlapping supported versions per minor version if len(filteredVersions) > 0 { - allErrs = append(allErrs, field.Forbidden(fldPath, fmt.Sprintf("unable to add version %q with classification %q. Only one %q version is allowed per minor version", version.Version, core.ClassificationSupported, core.ClassificationSupported))) + for _, possibleOverlap := range filteredVersions { + if supportedVersionsOverlapping(version, possibleOverlap) { + allErrs = append(allErrs, field.Forbidden(fldPath, fmt.Sprintf("unable to add version %q with classification %q. %q lifecycle stages must not overlap per minor version", version.Version, core.ClassificationSupported, core.ClassificationSupported))) + } + } } } return allErrs } +// supportedVersionsOverlapping checks whether supported classifications do overlap. Start time equality is not deemed an overlap in this context. +func supportedVersionsOverlapping(v1, v2 core.ExpirableVersion) bool { + if len(v1.Lifecycle) == 0 || len(v2.Lifecycle) == 0 { + return true + } + + supportedStage := helper.SupportedLifecycleClassification(v1) + nextStage := findLifecycleStageAbove(v1, supportedStage.Classification) + supportedStage2 := helper.SupportedLifecycleClassification(v2) + nextStage2 := findLifecycleStageAbove(v2, supportedStage2.Classification) + + if supportedStage.Classification != core.ClassificationSupported || + supportedStage.Classification != supportedStage2.Classification { + return false + } + if nextStage == nil && nextStage2 == nil || // Eventually both supported classifications will be supported simultaneously + nextStage == nil && (supportedStage.StartTime == nil || supportedStage.StartTime.Before(nextStage2.StartTime)) || // supportedStage has no subsequent classification and starts before nextStage2 + nextStage2 == nil && (supportedStage2.StartTime == nil || supportedStage2.StartTime.Before(nextStage.StartTime)) { // supportedStage2 has no subsequent classification and starts before nextStage + return true + } + return false +} + +func findLifecycleStageAbove(version core.ExpirableVersion, classification core.VersionClassification) *core.LifecycleStage { + for _, stage := range version.Lifecycle { + if stage.Classification.Compare(classification) > 0 { + return &stage + } + } + return nil +} + func validateCloudProfileMachineTypes(machineTypes []core.MachineType, fldPath *field.Path) field.ErrorList { allErrs := field.ErrorList{} @@ -163,6 +267,7 @@ func ValidateCloudProfileMachineImages(machineImages []core.MachineImage, fldPat for index, machineVersion := range image.Versions { versionsPath := idxPath.Child("versions").Index(index) allErrs = append(allErrs, validateContainerRuntimesInterfaces(machineVersion.CRI, versionsPath.Child("cri"))...) + allErrs = append(allErrs, validateExpirableVersion(machineVersion.ExpirableVersion, versionsPath)...) allErrs = append(allErrs, validateSupportedVersionsConfiguration(machineVersion.ExpirableVersion, helper.ToExpirableVersions(image.Versions), versionsPath)...) if len(machineVersion.Architectures) == 0 { diff --git a/pkg/apis/core/validation/cloudprofile_test.go b/pkg/apis/core/validation/cloudprofile_test.go index b0fe4e27668..4aa154ae8c0 100644 --- a/pkg/apis/core/validation/cloudprofile_test.go +++ b/pkg/apis/core/validation/cloudprofile_test.go @@ -104,6 +104,7 @@ var ( supportedClassification = core.ClassificationSupported previewClassification = core.ClassificationPreview deprecatedClassification = core.ClassificationDeprecated + expiredClassification = core.ClassificationExpired updateStrategyMajor = core.MachineImageUpdateStrategy("major") ) @@ -173,6 +174,31 @@ var _ = Describe("CloudProfile Validation Tests ", func() { }, }, } + duplicatedMachineImage = []core.MachineImage{ + { + Name: "ubuntu", + Versions: []core.MachineImageVersion{ + { + ExpirableVersion: core.ExpirableVersion{ + Version: "3.4.6", + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + { + ExpirableVersion: core.ExpirableVersion{ + Version: "3.4.6", + Lifecycle: []core.LifecycleStage{ + {Classification: previewClassification}, + }, + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + }, + UpdateStrategy: &updateStrategyMajor, + }, + } ) BeforeEach(func() { @@ -309,7 +335,7 @@ var _ = Describe("CloudProfile Validation Tests ", func() { })))) }) - It("should forbid expiration date on latest kubernetes version", func() { + It("should forbid (deprecated) expiration date on latest kubernetes version", func() { expirationDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ { @@ -331,6 +357,232 @@ var _ = Describe("CloudProfile Validation Tests ", func() { })))) }) + It("should forbid expired lifecycle stage on latest kubernetes version", func() { + expirationDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} + cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + }, + }, + { + Version: "1.2.0", + Lifecycle: []core.LifecycleStage{ + {Classification: deprecatedClassification}, + {Classification: expiredClassification, StartTime: expirationDate}, + }, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeInvalid), + "Field": Equal("spec.kubernetes.versions[].lifecycle"), + })))) + }) + + It("should forbid specifying lifecycle and classification at the same time", func() { + deprecatedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} + cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.1.0", + Classification: &supportedClassification, + Lifecycle: []core.LifecycleStage{ + {Classification: deprecatedClassification, StartTime: deprecatedDate}, + }, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeForbidden), + "Field": Equal("spec.kubernetes.versions[0]"), + })))) + }) + + It("should allow multiple directly following lifecycle stages with same start time", func() { + supportedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} + + cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification, StartTime: supportedDate}, + {Classification: deprecatedClassification, StartTime: supportedDate}, + }, + }, + { + Version: "1.2.0", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + }, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(BeEmpty()) + }) + + It("should forbid multiple lifecycle stages with same classification", func() { + supportedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} + cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + {Classification: supportedClassification, StartTime: supportedDate}, + }, + }, + { + Version: "1.2.0", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + }, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeInvalid), + "Field": Equal("spec.kubernetes.versions[0].lifecycle"), + "Detail": Equal("duplicate classification stage in lifecycle"), + })))) + }) + + It("should forbid unordered lifecycle stages", func() { + now := time.Now() + + cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []core.LifecycleStage{ + {Classification: previewClassification}, + {Classification: deprecatedClassification, StartTime: ptr.To(metav1.NewTime(now.Add(1 * time.Hour)))}, + {Classification: supportedClassification, StartTime: ptr.To(metav1.NewTime(now.Add(3 * time.Hour)))}, + }, + }, + { + Version: "1.2.0", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + }, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeInvalid), + "Field": Equal("spec.kubernetes.versions[0].lifecycle"), + "Detail": Equal("lifecycle classifications not in order, must be preview -> supported -> deprecated -> expired"), + })))) + }) + + It("should forbid missing start time for subsequent lifecycle stages", func() { + previewDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} + deprecatedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 3)} + cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []core.LifecycleStage{ + {Classification: previewClassification, StartTime: previewDate}, + {Classification: supportedClassification}, + {Classification: deprecatedClassification, StartTime: deprecatedDate}, + }, + }, + { + Version: "1.2.0", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + }, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeInvalid), + "Field": Equal("spec.kubernetes.versions[0].lifecycle[1]"), + "Detail": Equal("only the leading lifecycle elements can have the start time optional"), + })))) + }) + + It("should forbid lifecycle start times that are not monotonically increasing", func() { + now := time.Now() + + cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []core.LifecycleStage{ + {Classification: previewClassification, StartTime: ptr.To(metav1.NewTime(now.Add(0 * time.Hour)))}, + {Classification: supportedClassification, StartTime: ptr.To(metav1.NewTime(now.Add(2 * time.Hour)))}, + {Classification: deprecatedClassification, StartTime: ptr.To(metav1.NewTime(now.Add(1 * time.Hour)))}, + }, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeInvalid), + "Field": Equal("spec.kubernetes.versions[0].lifecycle[2]"), + "Detail": Equal("lifecycle start times must be monotonically increasing"), + })))) + }) + + It("should allow multiple missing start times for leading lifecycle stages", func() { + cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []core.LifecycleStage{ + {Classification: previewClassification}, + {Classification: supportedClassification}, + {Classification: deprecatedClassification}, + }, + }, + { + Version: "1.2.0", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + }, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(BeEmpty()) + }) + + It("should allow missing start time for first lifecycle stage", func() { + supportedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} + deprecatedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 2)} + cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []core.LifecycleStage{ + {Classification: previewClassification}, + {Classification: supportedClassification, StartTime: supportedDate}, + {Classification: deprecatedClassification, StartTime: deprecatedDate}, + }, + }, + { + Version: "1.2.0", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + }, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(BeEmpty()) + }) + It("should forbid duplicated kubernetes versions", func() { cloudProfile.Spec.Kubernetes = duplicatedKubernetes @@ -358,6 +610,7 @@ var _ = Describe("CloudProfile Validation Tests ", func() { "Type": Equal(field.ErrorTypeNotSupported), "Field": Equal("spec.kubernetes.versions[0].classification"), "BadValue": Equal(classification), + "Detail": Equal(`supported values: "deprecated", "expired", "preview", "supported", "unavailable"`), })))) }) @@ -382,9 +635,302 @@ var _ = Describe("CloudProfile Validation Tests ", func() { "Field": Equal("spec.kubernetes.versions[0]"), })))) }) + + It("only allow one supported version per minor version using Lifecycle", func() { + time1 := metav1.Now() + time2 := metav1.Time{Time: metav1.Now().Add(time.Hour)} + time3 := metav1.Time{Time: metav1.Now().Add(2 * time.Hour)} + cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []core.LifecycleStage{ + {Classification: previewClassification}, + {Classification: supportedClassification, StartTime: &time1}, + {Classification: deprecatedClassification, StartTime: &time3}, + }, + }, + { + Version: "1.1.1", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification, StartTime: &time2}, + }, + }, + } + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeForbidden), + "Field": Equal("spec.kubernetes.versions[0]"), + "Detail": ContainSubstring("\"supported\" lifecycle stages must not overlap per minor version"), + })))) + }) + + It("allow multiple supported version per minor version if their lifecycle start times do not overlap", func() { + time1 := metav1.Now() + time3 := metav1.Time{Time: metav1.Now().Add(2 * time.Hour)} + cloudProfile.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []core.LifecycleStage{ + {Classification: previewClassification}, + {Classification: supportedClassification, StartTime: &time1}, + {Classification: deprecatedClassification, StartTime: &time3}, + }, + }, + { + Version: "1.1.1", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification, StartTime: &time3}, + }, + }, + } + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(BeEmpty()) + }) }) Context("machine image validation", func() { + It("should forbid specifying lifecycle and classification at the same time", func() { + deprecatedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} + cloudProfile.Spec.MachineImages = []core.MachineImage{ + { + Name: "ubuntu", + Versions: []core.MachineImageVersion{ + { + ExpirableVersion: core.ExpirableVersion{ + Version: "3.4.6", + Classification: &supportedClassification, + Lifecycle: []core.LifecycleStage{ + {Classification: deprecatedClassification, StartTime: deprecatedDate}, + }, + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + }, + UpdateStrategy: &updateStrategyMajor, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeForbidden), + "Field": Equal("spec.machineImages[0].versions[0]"), + "Detail": Equal("cannot specify `classification` or `expirationDate` in combination with `lifecycle`"), + })))) + }) + + It("should allow multiple lifecycle stages with same start time", func() { + supportedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} + cloudProfile.Spec.MachineImages = []core.MachineImage{ + { + Name: "ubuntu", + Versions: []core.MachineImageVersion{ + { + ExpirableVersion: core.ExpirableVersion{ + Version: "3.4.6", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification, StartTime: supportedDate}, + }, + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + { + ExpirableVersion: core.ExpirableVersion{ + Version: "4.4.6", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification, StartTime: supportedDate}, + {Classification: deprecatedClassification, StartTime: supportedDate}, + }, + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + }, + UpdateStrategy: &updateStrategyMajor, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(BeEmpty()) + }) + + It("should forbid multiple lifecycle stages with same classification", func() { + supportedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} + + cloudProfile.Spec.MachineImages = []core.MachineImage{ + { + Name: "ubuntu", + Versions: []core.MachineImageVersion{ + { + ExpirableVersion: core.ExpirableVersion{ + Version: "3.4.6", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + }, + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + { + ExpirableVersion: core.ExpirableVersion{ + Version: "4.4.6", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + {Classification: supportedClassification, StartTime: supportedDate}, + }, + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + }, + UpdateStrategy: &updateStrategyMajor, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeInvalid), + "Field": Equal("spec.machineImages[0].versions[1].lifecycle"), + "Detail": Equal("duplicate classification stage in lifecycle"), + })))) + }) + + It("should forbid unordered lifecycle stages", func() { + now := time.Now() + + cloudProfile.Spec.MachineImages = []core.MachineImage{ + { + Name: "ubuntu", + Versions: []core.MachineImageVersion{ + { + ExpirableVersion: core.ExpirableVersion{ + Version: "3.4.6", + Lifecycle: []core.LifecycleStage{ + {Classification: previewClassification}, + {Classification: deprecatedClassification, StartTime: ptr.To(metav1.NewTime(now.Add(1 * time.Hour)))}, + {Classification: supportedClassification, StartTime: ptr.To(metav1.NewTime(now.Add(2 * time.Hour)))}, + }, + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + { + ExpirableVersion: core.ExpirableVersion{ + Version: "4.4.6", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + }, + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + }, + UpdateStrategy: &updateStrategyMajor, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeInvalid), + "Field": Equal("spec.machineImages[0].versions[0].lifecycle"), + "Detail": Equal("lifecycle classifications not in order, must be preview -> supported -> deprecated -> expired"), + })))) + }) + + It("should forbid missing start time for subsequent lifecycle stages", func() { + supportedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} + + cloudProfile.Spec.MachineImages = []core.MachineImage{ + { + Name: "ubuntu", + Versions: []core.MachineImageVersion{ + { + ExpirableVersion: core.ExpirableVersion{ + Version: "3.4.6", + Lifecycle: []core.LifecycleStage{ + {Classification: previewClassification}, + {Classification: supportedClassification, StartTime: supportedDate}, + {Classification: deprecatedClassification}, + }, + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + { + ExpirableVersion: core.ExpirableVersion{ + Version: "4.4.6", + Lifecycle: []core.LifecycleStage{ + {Classification: supportedClassification}, + }, + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + }, + UpdateStrategy: &updateStrategyMajor, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeInvalid), + "Field": Equal("spec.machineImages[0].versions[0].lifecycle[2]"), + "Detail": Equal("only the leading lifecycle elements can have the start time optional"), + })))) + }) + + It("should forbid duplicated machineImage versions", func() { + cloudProfile.Spec.MachineImages = duplicatedMachineImage + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf( + PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeDuplicate), + "Field": Equal(fmt.Sprintf("spec.machineImages[0].versions[%d]", len(duplicatedMachineImage[0].Versions)-1)), + })))) + }) + + It("should forbid invalid classification for machineImage versions", func() { + invalidClassification := core.VersionClassification("dummy") + + cloudProfile.Spec.MachineImages = []core.MachineImage{ + { + Name: "ubuntu", + Versions: []core.MachineImageVersion{ + { + ExpirableVersion: core.ExpirableVersion{ + Version: "3.4.6", + Lifecycle: []core.LifecycleStage{ + {Classification: invalidClassification}, + }, + }, + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + }, + }, + UpdateStrategy: &updateStrategyMajor, + }, + } + + errorList := ValidateCloudProfile(cloudProfile) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeNotSupported), + "Field": Equal("spec.machineImages[0].versions[0].lifecycle[0].classification"), + "BadValue": Equal(invalidClassification), + "Detail": Equal(`supported values: "deprecated", "expired", "preview", "supported", "unavailable"`), + })))) + }) + It("should forbid an empty list of machine images", func() { cloudProfile.Spec.MachineImages = []core.MachineImage{} @@ -1293,5 +1839,91 @@ var _ = Describe("CloudProfile Validation Tests ", func() { Expect(errorList).To(BeEmpty()) }) }) + + Context("Update version from supported to unavailable", func() { + It("should prevent a kubernetes version update to unavailable when it was already active", func() { + now := time.Now() + + cloudProfileNew.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.17.2", + Lifecycle: []core.LifecycleStage{ + { + Classification: core.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(1 * time.Hour))), + }, + }, + }, + } + cloudProfileOld.Spec.Kubernetes.Versions = []core.ExpirableVersion{ + { + Version: "1.17.2", + Lifecycle: []core.LifecycleStage{ + { + Classification: core.ClassificationSupported, + }, + }, + }, + } + errorList := ValidateCloudProfileUpdate(cloudProfileNew, cloudProfileOld) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeForbidden), + "Field": Equal("spec.kubernetes.versions[0]"), + "Detail": Equal("a version cannot be turned into unavailable if it already was already moved into a later lifecycle stage"), + })))) + }) + + It("should prevent a machine image update to unavailable when it was already active", func() { + cloudProfileNew.Spec.MachineImages = []core.MachineImage{ + { + Name: "ubuntu", + UpdateStrategy: &updateStrategyMajor, + Versions: []core.MachineImageVersion{ + { + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + ExpirableVersion: core.ExpirableVersion{ + Version: "2135.6.0", + Lifecycle: []core.LifecycleStage{ + { + Classification: core.ClassificationUnavailable, + }, + }, + }, + }, + }, + }, + } + cloudProfileOld.Spec.MachineImages = []core.MachineImage{ + { + Name: "ubuntu", + UpdateStrategy: &updateStrategyMajor, + Versions: []core.MachineImageVersion{ + { + CRI: []core.CRI{{Name: "containerd"}}, + Architectures: []string{"amd64"}, + ExpirableVersion: core.ExpirableVersion{ + Version: "2135.6.0", + Lifecycle: []core.LifecycleStage{ + { + Classification: core.ClassificationPreview, + }, + }, + }, + }, + }, + }, + } + + errorList := ValidateCloudProfileUpdate(cloudProfileNew, cloudProfileOld) + + Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ + "Type": Equal(field.ErrorTypeForbidden), + "Field": Equal("spec.machineImages[0].versions[0]"), + "Detail": Equal("a version cannot be turned into unavailable if it already was already moved into a later lifecycle stage"), + })))) + }) + }) }) }) diff --git a/pkg/apis/core/validation/namespacedcloudprofile.go b/pkg/apis/core/validation/namespacedcloudprofile.go index 26c7bb82287..0d5a6e29bba 100644 --- a/pkg/apis/core/validation/namespacedcloudprofile.go +++ b/pkg/apis/core/validation/namespacedcloudprofile.go @@ -20,6 +20,7 @@ func ValidateNamespacedCloudProfile(namespacedCloudProfile *core.NamespacedCloud allErrs = append(allErrs, validateNamespacedCloudProfileParent(namespacedCloudProfile.Spec.Parent, field.NewPath("spec.parent"))...) allErrs = append(allErrs, validateNamespacedCloudProfileKubernetesVersions(namespacedCloudProfile.Spec.Kubernetes, field.NewPath("spec.kubernetes"))...) + allErrs = append(allErrs, validateCloudProfileKubernetesClassificationLifecycleStartTimesOrder(namespacedCloudProfile.Spec.Kubernetes, field.NewPath("spec.kubernetes"))...) allErrs = append(allErrs, ValidateMachineImages(namespacedCloudProfile.Spec.MachineImages, field.NewPath("spec.machineImages"))...) allErrs = append(allErrs, validateVolumeTypes(namespacedCloudProfile.Spec.VolumeTypes, field.NewPath("spec.volumeTypes"))...) allErrs = append(allErrs, validateMachineTypes(namespacedCloudProfile.Spec.MachineTypes, field.NewPath("spec.machineTypes"))...) diff --git a/pkg/apis/core/validation/utils.go b/pkg/apis/core/validation/utils.go index 82444a1a75c..767f4cec1fb 100644 --- a/pkg/apis/core/validation/utils.go +++ b/pkg/apis/core/validation/utils.go @@ -10,11 +10,13 @@ import ( "slices" "strconv" "strings" + "time" "github.com/Masterminds/semver/v3" autoscalingv1 "k8s.io/api/autoscaling/v1" corev1 "k8s.io/api/core/v1" apivalidation "k8s.io/apimachinery/pkg/api/validation" + v1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/util/intstr" "k8s.io/apimachinery/pkg/util/sets" "k8s.io/apimachinery/pkg/util/validation" @@ -168,7 +170,7 @@ func ValidateIPFamilies(ipFamilies []core.IPFamily, fldPath *field.Path) field.E // k8sVersionCPRegex is used to validate kubernetes versions in a cloud profile. var k8sVersionCPRegex = regexp.MustCompile(`^([0-9]+\.){2}[0-9]+$`) -var supportedVersionClassifications = sets.New(string(core.ClassificationPreview), string(core.ClassificationSupported), string(core.ClassificationDeprecated)) +var supportedVersionClassifications = sets.New(string(core.ClassificationPreview), string(core.ClassificationSupported), string(core.ClassificationDeprecated), string(core.ClassificationExpired), string(core.ClassificationUnavailable)) // validateKubernetesVersions validates the given list of ExpirableVersions for valid Kubernetes versions. func validateKubernetesVersions(versions []core.ExpirableVersion, fldPath *field.Path) field.ErrorList { @@ -191,6 +193,124 @@ func validateKubernetesVersions(versions []core.ExpirableVersion, fldPath *field if version.Classification != nil && !supportedVersionClassifications.Has(string(*version.Classification)) { allErrs = append(allErrs, field.NotSupported(idxPath.Child("classification"), *version.Classification, sets.List(supportedVersionClassifications))) } + + allErrs = append(allErrs, validateExpirableVersion(version, idxPath)...) + } + + return allErrs +} + +// validateExpirableVersion validates the ExpirableVersions. +func validateExpirableVersion(version core.ExpirableVersion, fldPath *field.Path) field.ErrorList { + allErrs := field.ErrorList{} + + if (version.Classification != nil || version.ExpirationDate != nil) && len(version.Lifecycle) > 0 { + allErrs = append(allErrs, field.Forbidden(fldPath, "cannot specify `classification` or `expirationDate` in combination with `lifecycle`")) + } + + lifecyclePath := fldPath.Child("lifecycle") + + allErrs = append(allErrs, validateLifecycleClassificationsValid(version.Lifecycle, lifecyclePath)...) + allErrs = append(allErrs, validateLifecycleNoDuplicates(version.Lifecycle, lifecyclePath)...) + allErrs = append(allErrs, validateLifecycleInOrder(version.Lifecycle, lifecyclePath)...) + allErrs = append(allErrs, validateLifecycleStartTimes(version.Lifecycle, lifecyclePath)...) + + return allErrs +} + +// validateLifecycleClassificationsValid checks if the given classification in the lifecycle are in the list of supported version classifications. +func validateLifecycleClassificationsValid(lifecycle []core.LifecycleStage, fldPath *field.Path) field.ErrorList { + allErrs := field.ErrorList{} + + for i, l := range lifecycle { + if !supportedVersionClassifications.Has(string(l.Classification)) { + validValues := supportedVersionClassifications.UnsortedList() + slices.Sort(validValues) + allErrs = append(allErrs, field.NotSupported(fldPath.Index(i).Child("classification"), l.Classification, validValues)) + } + } + + return allErrs +} + +// validateLifecycleNoDuplicates checks if there are any duplicate entries in the provided lifecycle slice +func validateLifecycleNoDuplicates(lifecycle []core.LifecycleStage, fldPath *field.Path) field.ErrorList { + var ( + allErrs = field.ErrorList{} + duplicates = sets.NewString() + seen = make(map[core.VersionClassification]bool) + ) + + for _, value := range lifecycle { + classification := value.Classification + + if seen[classification] { + duplicates.Insert(string(classification)) + } + + seen[classification] = true + } + + for _, duplicate := range duplicates.List() { + allErrs = append(allErrs, field.Invalid(fldPath, duplicate, "duplicate classification stage in lifecycle")) + } + + return allErrs +} + +// validateLifecycleInOrder checks if the provided lifecycle slice is in the expected order. +// The order is not required for functionality but should ensure better readability. +func validateLifecycleInOrder(lifecycle []core.LifecycleStage, fldPath *field.Path) field.ErrorList { + var allErrs = field.ErrorList{} + + var misplacedElement core.VersionClassification + isSorted := slices.IsSortedFunc(lifecycle, func(a, b core.LifecycleStage) int { + orderResult := a.Classification.Compare(b.Classification) + if orderResult > 0 { + misplacedElement = a.Classification + } + return orderResult + }) + if !isSorted { + allErrs = append(allErrs, field.Invalid(fldPath, misplacedElement, "lifecycle classifications not in order, must be preview -> supported -> deprecated -> expired")) + } + + return allErrs +} + +// validateLifecycleStartTimes checks if the given slice of lifecycles has start times in order. +// and that only the leading lifecycle classification has no startTime. +// As soon as one lifecycle classification did contain a startTime, all following must have a startTime, too. +// It does not ensure the correct order of the classifications but if the elements in the +// list have dates after each other. The order must be tested via `validateLifecycleInOrder`. +func validateLifecycleStartTimes(lifecycle []core.LifecycleStage, fldPath *field.Path) field.ErrorList { + var ( + allErrs = field.ErrorList{} + previousStartTime *time.Time + ) + + for i, l := range lifecycle { + if previousStartTime == nil { + if l.StartTime == nil { + l.StartTime = &v1.Time{} + } else { + previousStartTime = &l.StartTime.Time + } + continue + } + + if l.StartTime == nil { + allErrs = append(allErrs, field.Invalid(fldPath.Index(i), l.Classification, "only the leading lifecycle elements can have the start time optional")) + continue + } + + currentStartTime := l.StartTime.Time + + if currentStartTime.Before(*previousStartTime) { + allErrs = append(allErrs, field.Invalid(fldPath.Index(i), l.StartTime.String(), "lifecycle start times must be monotonically increasing")) + } + + previousStartTime = ¤tStartTime } return allErrs diff --git a/pkg/apis/core/zz_generated.deepcopy.go b/pkg/apis/core/zz_generated.deepcopy.go index bdcf7e9c587..f7dd1d3be91 100644 --- a/pkg/apis/core/zz_generated.deepcopy.go +++ b/pkg/apis/core/zz_generated.deepcopy.go @@ -670,6 +670,7 @@ func (in *CloudProfile) DeepCopyInto(out *CloudProfile) { out.TypeMeta = in.TypeMeta in.ObjectMeta.DeepCopyInto(&out.ObjectMeta) in.Spec.DeepCopyInto(&out.Spec) + in.Status.DeepCopyInto(&out.Status) return } @@ -805,6 +806,34 @@ func (in *CloudProfileSpec) DeepCopy() *CloudProfileSpec { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *CloudProfileStatus) DeepCopyInto(out *CloudProfileStatus) { + *out = *in + if in.KubernetesVersions != nil { + in, out := &in.KubernetesVersions, &out.KubernetesVersions + *out = make([]ExpirableVersionStatus, len(*in)) + copy(*out, *in) + } + if in.MachineImageVersions != nil { + in, out := &in.MachineImageVersions, &out.MachineImageVersions + *out = make([]MachineImageVersionStatus, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CloudProfileStatus. +func (in *CloudProfileStatus) DeepCopy() *CloudProfileStatus { + if in == nil { + return nil + } + out := new(CloudProfileStatus) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ClusterAutoscaler) DeepCopyInto(out *ClusterAutoscaler) { *out = *in @@ -1664,6 +1693,13 @@ func (in *ExpirableVersion) DeepCopyInto(out *ExpirableVersion) { *out = new(VersionClassification) **out = **in } + if in.Lifecycle != nil { + in, out := &in.Lifecycle, &out.Lifecycle + *out = make([]LifecycleStage, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } return } @@ -1677,6 +1713,22 @@ func (in *ExpirableVersion) DeepCopy() *ExpirableVersion { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ExpirableVersionStatus) DeepCopyInto(out *ExpirableVersionStatus) { + *out = *in + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ExpirableVersionStatus. +func (in *ExpirableVersionStatus) DeepCopy() *ExpirableVersionStatus { + if in == nil { + return nil + } + out := new(ExpirableVersionStatus) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ExposureClass) DeepCopyInto(out *ExposureClass) { *out = *in @@ -2833,6 +2885,26 @@ func (in *LastOperation) DeepCopy() *LastOperation { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *LifecycleStage) DeepCopyInto(out *LifecycleStage) { + *out = *in + if in.StartTime != nil { + in, out := &in.StartTime, &out.StartTime + *out = (*in).DeepCopy() + } + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new LifecycleStage. +func (in *LifecycleStage) DeepCopy() *LifecycleStage { + if in == nil { + return nil + } + out := new(LifecycleStage) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *LoadBalancerServicesProxyProtocol) DeepCopyInto(out *LoadBalancerServicesProxyProtocol) { *out = *in @@ -2978,6 +3050,27 @@ func (in *MachineImageVersion) DeepCopy() *MachineImageVersion { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *MachineImageVersionStatus) DeepCopyInto(out *MachineImageVersionStatus) { + *out = *in + if in.Versions != nil { + in, out := &in.Versions, &out.Versions + *out = make([]ExpirableVersionStatus, len(*in)) + copy(*out, *in) + } + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new MachineImageVersionStatus. +func (in *MachineImageVersionStatus) DeepCopy() *MachineImageVersionStatus { + if in == nil { + return nil + } + out := new(MachineImageVersionStatus) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *MachineType) DeepCopyInto(out *MachineType) { *out = *in diff --git a/pkg/apiserver/openapi/api_violations.report b/pkg/apiserver/openapi/api_violations.report index 0d7517a2429..b363db96833 100644 --- a/pkg/apiserver/openapi/api_violations.report +++ b/pkg/apiserver/openapi/api_violations.report @@ -6,6 +6,8 @@ API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,CloudProfileSpec,MachineTypes API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,CloudProfileSpec,Regions API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,CloudProfileSpec,VolumeTypes +API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,CloudProfileStatus,KubernetesVersions +API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,CloudProfileStatus,MachineImageVersions API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,ClusterAutoscaler,IgnoreTaints API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,ClusterAutoscaler,StartupTaints API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,ClusterAutoscaler,StatusTaints @@ -18,6 +20,7 @@ API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,DNSIncludeExclude,Exclude API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,DNSIncludeExclude,Include API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,EncryptionConfig,Resources +API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,ExpirableVersion,Lifecycle API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,ExposureClassScheduling,Tolerations API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,ExtensionResourceState,Resources API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,Hibernation,Schedules @@ -29,6 +32,7 @@ API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,MachineImage,Versions API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,MachineImageVersion,Architectures API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,MachineImageVersion,CRI +API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,MachineImageVersionStatus,Versions API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,NamespacedCloudProfileSpec,MachineImages API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,NamespacedCloudProfileSpec,MachineTypes API rule violation: list_type_missing,github.com/gardener/gardener/pkg/apis/core/v1beta1,NamespacedCloudProfileSpec,VolumeTypes diff --git a/pkg/apiserver/openapi/openapi_generated.go b/pkg/apiserver/openapi/openapi_generated.go index a920e171646..61a4ce00f15 100644 --- a/pkg/apiserver/openapi/openapi_generated.go +++ b/pkg/apiserver/openapi/openapi_generated.go @@ -61,6 +61,7 @@ func GetOpenAPIDefinitions(ref common.ReferenceCallback) map[string]common.OpenA "github.com/gardener/gardener/pkg/apis/core/v1beta1.CloudProfileList": schema_pkg_apis_core_v1beta1_CloudProfileList(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.CloudProfileReference": schema_pkg_apis_core_v1beta1_CloudProfileReference(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.CloudProfileSpec": schema_pkg_apis_core_v1beta1_CloudProfileSpec(ref), + "github.com/gardener/gardener/pkg/apis/core/v1beta1.CloudProfileStatus": schema_pkg_apis_core_v1beta1_CloudProfileStatus(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.ClusterAutoscaler": schema_pkg_apis_core_v1beta1_ClusterAutoscaler(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.ClusterAutoscalerOptions": schema_pkg_apis_core_v1beta1_ClusterAutoscalerOptions(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.Condition": schema_pkg_apis_core_v1beta1_Condition(ref), @@ -90,6 +91,7 @@ func GetOpenAPIDefinitions(ref common.ReferenceCallback) map[string]common.OpenA "github.com/gardener/gardener/pkg/apis/core/v1beta1.ETCDEncryptionKeyRotation": schema_pkg_apis_core_v1beta1_ETCDEncryptionKeyRotation(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.EncryptionConfig": schema_pkg_apis_core_v1beta1_EncryptionConfig(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.ExpirableVersion": schema_pkg_apis_core_v1beta1_ExpirableVersion(ref), + "github.com/gardener/gardener/pkg/apis/core/v1beta1.ExpirableVersionStatus": schema_pkg_apis_core_v1beta1_ExpirableVersionStatus(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.ExposureClass": schema_pkg_apis_core_v1beta1_ExposureClass(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.ExposureClassList": schema_pkg_apis_core_v1beta1_ExposureClassList(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.ExposureClassScheduling": schema_pkg_apis_core_v1beta1_ExposureClassScheduling(ref), @@ -123,11 +125,13 @@ func GetOpenAPIDefinitions(ref common.ReferenceCallback) map[string]common.OpenA "github.com/gardener/gardener/pkg/apis/core/v1beta1.LastError": schema_pkg_apis_core_v1beta1_LastError(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.LastMaintenance": schema_pkg_apis_core_v1beta1_LastMaintenance(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.LastOperation": schema_pkg_apis_core_v1beta1_LastOperation(ref), + "github.com/gardener/gardener/pkg/apis/core/v1beta1.LifecycleStage": schema_pkg_apis_core_v1beta1_LifecycleStage(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.LoadBalancerServicesProxyProtocol": schema_pkg_apis_core_v1beta1_LoadBalancerServicesProxyProtocol(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.Machine": schema_pkg_apis_core_v1beta1_Machine(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.MachineControllerManagerSettings": schema_pkg_apis_core_v1beta1_MachineControllerManagerSettings(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.MachineImage": schema_pkg_apis_core_v1beta1_MachineImage(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.MachineImageVersion": schema_pkg_apis_core_v1beta1_MachineImageVersion(ref), + "github.com/gardener/gardener/pkg/apis/core/v1beta1.MachineImageVersionStatus": schema_pkg_apis_core_v1beta1_MachineImageVersionStatus(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.MachineType": schema_pkg_apis_core_v1beta1_MachineType(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.MachineTypeStorage": schema_pkg_apis_core_v1beta1_MachineTypeStorage(ref), "github.com/gardener/gardener/pkg/apis/core/v1beta1.Maintenance": schema_pkg_apis_core_v1beta1_Maintenance(ref), @@ -1966,11 +1970,18 @@ func schema_pkg_apis_core_v1beta1_CloudProfile(ref common.ReferenceCallback) com Ref: ref("github.com/gardener/gardener/pkg/apis/core/v1beta1.CloudProfileSpec"), }, }, + "status": { + SchemaProps: spec.SchemaProps{ + Description: "Status contains the current status of the cloud profile.", + Default: map[string]interface{}{}, + Ref: ref("github.com/gardener/gardener/pkg/apis/core/v1beta1.CloudProfileStatus"), + }, + }, }, }, }, Dependencies: []string{ - "github.com/gardener/gardener/pkg/apis/core/v1beta1.CloudProfileSpec", "k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"}, + "github.com/gardener/gardener/pkg/apis/core/v1beta1.CloudProfileSpec", "github.com/gardener/gardener/pkg/apis/core/v1beta1.CloudProfileStatus", "k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"}, } } @@ -2191,6 +2202,49 @@ func schema_pkg_apis_core_v1beta1_CloudProfileSpec(ref common.ReferenceCallback) } } +func schema_pkg_apis_core_v1beta1_CloudProfileStatus(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "CloudProfileStatus contains the status of the cloud profile.", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "kubernetesVersions": { + SchemaProps: spec.SchemaProps{ + Description: "KubernetesVersions contains the statuses of the kubernetes versions.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("github.com/gardener/gardener/pkg/apis/core/v1beta1.ExpirableVersionStatus"), + }, + }, + }, + }, + }, + "machineImageVersions": { + SchemaProps: spec.SchemaProps{ + Description: "MachineImageVersions contains the statuses of the machine image versions.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("github.com/gardener/gardener/pkg/apis/core/v1beta1.MachineImageVersionStatus"), + }, + }, + }, + }, + }, + }, + }, + }, + Dependencies: []string{ + "github.com/gardener/gardener/pkg/apis/core/v1beta1.ExpirableVersionStatus", "github.com/gardener/gardener/pkg/apis/core/v1beta1.MachineImageVersionStatus"}, + } +} + func schema_pkg_apis_core_v1beta1_ClusterAutoscaler(ref common.ReferenceCallback) common.OpenAPIDefinition { return common.OpenAPIDefinition{ Schema: spec.Schema{ @@ -3466,23 +3520,66 @@ func schema_pkg_apis_core_v1beta1_ExpirableVersion(ref common.ReferenceCallback) }, "expirationDate": { SchemaProps: spec.SchemaProps{ - Description: "ExpirationDate defines the time at which this version expires.", + Description: "Deprecated: Is replaced by Lifecycle.", Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.Time"), }, }, "classification": { SchemaProps: spec.SchemaProps{ - Description: "Classification defines the state of a version (preview, supported, deprecated)", + Description: "Classification defines the state of a version (preview, supported, deprecated). Deprecated: Is replaced by Lifecycle.", Type: []string{"string"}, Format: "", }, }, + "lifecycle": { + SchemaProps: spec.SchemaProps{ + Description: "Lifecycle defines the lifecycle stages for this version. Cannot be used in combination with Classification and ExpirationDate.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("github.com/gardener/gardener/pkg/apis/core/v1beta1.LifecycleStage"), + }, + }, + }, + }, + }, }, Required: []string{"version"}, }, }, Dependencies: []string{ - "k8s.io/apimachinery/pkg/apis/meta/v1.Time"}, + "github.com/gardener/gardener/pkg/apis/core/v1beta1.LifecycleStage", "k8s.io/apimachinery/pkg/apis/meta/v1.Time"}, + } +} + +func schema_pkg_apis_core_v1beta1_ExpirableVersionStatus(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "ExpirableVersionStatus defines the current status of an expirable version.", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "version": { + SchemaProps: spec.SchemaProps{ + Description: "Version is the version identifier.", + Default: "", + Type: []string{"string"}, + Format: "", + }, + }, + "classificationState": { + SchemaProps: spec.SchemaProps{ + Description: "ClassificationState reflects the current state in the classification lifecycle.", + Type: []string{"string"}, + Format: "", + }, + }, + }, + Required: []string{"version"}, + }, + }, } } @@ -5190,6 +5287,35 @@ func schema_pkg_apis_core_v1beta1_LastOperation(ref common.ReferenceCallback) co } } +func schema_pkg_apis_core_v1beta1_LifecycleStage(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "classification": { + SchemaProps: spec.SchemaProps{ + Description: "Classification is the category of this lifecycle stage (unavailable, preview, supported, deprecated, expired).", + Default: "", + Type: []string{"string"}, + Format: "", + }, + }, + "startTime": { + SchemaProps: spec.SchemaProps{ + Description: "StartTime defines when this lifecycle stage becomes active.", + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.Time"), + }, + }, + }, + Required: []string{"classification"}, + }, + }, + Dependencies: []string{ + "k8s.io/apimachinery/pkg/apis/meta/v1.Time"}, + } +} + func schema_pkg_apis_core_v1beta1_LoadBalancerServicesProxyProtocol(ref common.ReferenceCallback) common.OpenAPIDefinition { return common.OpenAPIDefinition{ Schema: spec.Schema{ @@ -5372,17 +5498,31 @@ func schema_pkg_apis_core_v1beta1_MachineImageVersion(ref common.ReferenceCallba }, "expirationDate": { SchemaProps: spec.SchemaProps{ - Description: "ExpirationDate defines the time at which this version expires.", + Description: "Deprecated: Is replaced by Lifecycle.", Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.Time"), }, }, "classification": { SchemaProps: spec.SchemaProps{ - Description: "Classification defines the state of a version (preview, supported, deprecated)", + Description: "Classification defines the state of a version (preview, supported, deprecated). Deprecated: Is replaced by Lifecycle.", Type: []string{"string"}, Format: "", }, }, + "lifecycle": { + SchemaProps: spec.SchemaProps{ + Description: "Lifecycle defines the lifecycle stages for this version. Cannot be used in combination with Classification and ExpirationDate.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("github.com/gardener/gardener/pkg/apis/core/v1beta1.LifecycleStage"), + }, + }, + }, + }, + }, "cri": { SchemaProps: spec.SchemaProps{ Description: "CRI list of supported container runtime and interfaces supported by this version", @@ -5424,7 +5564,42 @@ func schema_pkg_apis_core_v1beta1_MachineImageVersion(ref common.ReferenceCallba }, }, Dependencies: []string{ - "github.com/gardener/gardener/pkg/apis/core/v1beta1.CRI", "k8s.io/apimachinery/pkg/apis/meta/v1.Time"}, + "github.com/gardener/gardener/pkg/apis/core/v1beta1.CRI", "github.com/gardener/gardener/pkg/apis/core/v1beta1.LifecycleStage", "k8s.io/apimachinery/pkg/apis/meta/v1.Time"}, + } +} + +func schema_pkg_apis_core_v1beta1_MachineImageVersionStatus(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "name": { + SchemaProps: spec.SchemaProps{ + Description: "Name matches the name of the MachineImage the status is represented of.", + Type: []string{"string"}, + Format: "", + }, + }, + "versions": { + SchemaProps: spec.SchemaProps{ + Description: "Versions contains the statuses of the machine image versions.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("github.com/gardener/gardener/pkg/apis/core/v1beta1.ExpirableVersionStatus"), + }, + }, + }, + }, + }, + }, + }, + }, + Dependencies: []string{ + "github.com/gardener/gardener/pkg/apis/core/v1beta1.ExpirableVersionStatus"}, } } diff --git a/pkg/client/core/clientset/versioned/typed/core/v1beta1/cloudprofile.go b/pkg/client/core/clientset/versioned/typed/core/v1beta1/cloudprofile.go index bbdc77ad2f6..68740c67364 100644 --- a/pkg/client/core/clientset/versioned/typed/core/v1beta1/cloudprofile.go +++ b/pkg/client/core/clientset/versioned/typed/core/v1beta1/cloudprofile.go @@ -27,6 +27,8 @@ type CloudProfilesGetter interface { type CloudProfileInterface interface { Create(ctx context.Context, cloudProfile *v1beta1.CloudProfile, opts v1.CreateOptions) (*v1beta1.CloudProfile, error) Update(ctx context.Context, cloudProfile *v1beta1.CloudProfile, opts v1.UpdateOptions) (*v1beta1.CloudProfile, error) + // Add a +genclient:noStatus comment above the type to avoid generating UpdateStatus(). + UpdateStatus(ctx context.Context, cloudProfile *v1beta1.CloudProfile, opts v1.UpdateOptions) (*v1beta1.CloudProfile, error) Delete(ctx context.Context, name string, opts v1.DeleteOptions) error DeleteCollection(ctx context.Context, opts v1.DeleteOptions, listOpts v1.ListOptions) error Get(ctx context.Context, name string, opts v1.GetOptions) (*v1beta1.CloudProfile, error) diff --git a/pkg/client/core/clientset/versioned/typed/core/v1beta1/fake/fake_cloudprofile.go b/pkg/client/core/clientset/versioned/typed/core/v1beta1/fake/fake_cloudprofile.go index c1c653efaa0..8c9d1b7e3b1 100644 --- a/pkg/client/core/clientset/versioned/typed/core/v1beta1/fake/fake_cloudprofile.go +++ b/pkg/client/core/clientset/versioned/typed/core/v1beta1/fake/fake_cloudprofile.go @@ -87,6 +87,18 @@ func (c *FakeCloudProfiles) Update(ctx context.Context, cloudProfile *v1beta1.Cl return obj.(*v1beta1.CloudProfile), err } +// UpdateStatus was generated because the type contains a Status member. +// Add a +genclient:noStatus comment above the type to avoid generating UpdateStatus(). +func (c *FakeCloudProfiles) UpdateStatus(ctx context.Context, cloudProfile *v1beta1.CloudProfile, opts v1.UpdateOptions) (result *v1beta1.CloudProfile, err error) { + emptyResult := &v1beta1.CloudProfile{} + obj, err := c.Fake. + Invokes(testing.NewRootUpdateSubresourceActionWithOptions(cloudprofilesResource, "status", cloudProfile, opts), emptyResult) + if obj == nil { + return emptyResult, err + } + return obj.(*v1beta1.CloudProfile), err +} + // Delete takes name of the cloudProfile and deletes it. Returns an error if one occurs. func (c *FakeCloudProfiles) Delete(ctx context.Context, name string, opts v1.DeleteOptions) error { _, err := c.Fake. diff --git a/pkg/controllermanager/controller/cloudprofile/reconciler.go b/pkg/controllermanager/controller/cloudprofile/reconciler.go index 87ef226dcda..96c78872177 100644 --- a/pkg/controllermanager/controller/cloudprofile/reconciler.go +++ b/pkg/controllermanager/controller/cloudprofile/reconciler.go @@ -20,6 +20,7 @@ import ( gardencorev1beta1 "github.com/gardener/gardener/pkg/apis/core/v1beta1" v1beta1constants "github.com/gardener/gardener/pkg/apis/core/v1beta1/constants" + "github.com/gardener/gardener/pkg/apis/core/v1beta1/helper" "github.com/gardener/gardener/pkg/controllermanager/apis/config" "github.com/gardener/gardener/pkg/controllerutils" ) @@ -100,5 +101,39 @@ func (r *Reconciler) Reconcile(ctx context.Context, request reconcile.Request) ( } } + cloudProfile.Status = status(cloudProfile) + + if err := r.Client.Status().Update(ctx, cloudProfile); err != nil { + return reconcile.Result{}, err + } + return reconcile.Result{}, nil } + +func status(cloudProfile *gardencorev1beta1.CloudProfile) gardencorev1beta1.CloudProfileStatus { + var result gardencorev1beta1.CloudProfileStatus + + for _, version := range cloudProfile.Spec.Kubernetes.Versions { + result.KubernetesVersions = append(result.KubernetesVersions, gardencorev1beta1.ExpirableVersionStatus{ + Version: version.Version, + ClassificationState: helper.CurrentLifecycleClassification(version), + }) + } + + for _, machineImage := range cloudProfile.Spec.MachineImages { + status := gardencorev1beta1.MachineImageVersionStatus{ + Name: machineImage.Name, + } + + for _, version := range machineImage.Versions { + status.Versions = append(status.Versions, gardencorev1beta1.ExpirableVersionStatus{ + Version: version.Version, + ClassificationState: helper.CurrentLifecycleClassification(version.ExpirableVersion), + }) + } + + result.MachineImageVersions = append(result.MachineImageVersions, status) + } + + return result +} diff --git a/pkg/controllermanager/controller/cloudprofile/reconciler_test.go b/pkg/controllermanager/controller/cloudprofile/reconciler_test.go index 358d0eaae77..22572dfc5ef 100644 --- a/pkg/controllermanager/controller/cloudprofile/reconciler_test.go +++ b/pkg/controllermanager/controller/cloudprofile/reconciler_test.go @@ -8,6 +8,7 @@ import ( "context" "errors" "fmt" + "time" . "github.com/onsi/ginkgo/v2" . "github.com/onsi/gomega" @@ -17,6 +18,7 @@ import ( "k8s.io/apimachinery/pkg/runtime/schema" "k8s.io/apimachinery/pkg/types" "k8s.io/client-go/tools/record" + "k8s.io/utils/ptr" "sigs.k8s.io/controller-runtime/pkg/client" "sigs.k8s.io/controller-runtime/pkg/reconcile" @@ -29,9 +31,10 @@ var _ = Describe("Reconciler", func() { const finalizerName = "gardener" var ( - ctx = context.TODO() - ctrl *gomock.Controller - c *mockclient.MockClient + ctx = context.TODO() + ctrl *gomock.Controller + c *mockclient.MockClient + status *mockclient.MockStatusWriter cloudProfileName string fakeErr error @@ -42,6 +45,7 @@ var _ = Describe("Reconciler", func() { BeforeEach(func() { ctrl = gomock.NewController(GinkgoT()) c = mockclient.NewMockClient(ctrl) + status = mockclient.NewMockStatusWriter(ctrl) cloudProfileName = "test-cloudprofile" fakeErr = errors.New("fake err") @@ -101,6 +105,12 @@ var _ = Describe("Reconciler", func() { return nil }) + c.EXPECT().Status().Return(status) + expect := cloudProfile.DeepCopy() + expect.Finalizers = []string{finalizerName} + + status.EXPECT().Update(gomock.Any(), expect).Return(nil) + result, err := reconciler.Reconcile(ctx, reconcile.Request{NamespacedName: types.NamespacedName{Name: cloudProfileName}}) Expect(result).To(Equal(reconcile.Result{})) Expect(err).NotTo(HaveOccurred()) @@ -210,4 +220,70 @@ var _ = Describe("Reconciler", func() { Expect(err).NotTo(HaveOccurred()) }) }) + + Context("status reconciliation", func() { + BeforeEach(func() { + cloudProfile.Finalizers = []string{finalizerName} + }) + + var ( + testStatus = func(spec gardencorev1beta1.CloudProfileSpec, wantStatus gardencorev1beta1.CloudProfileStatus) { + cloudProfile.Spec = spec + + c.EXPECT().Get(gomock.Any(), client.ObjectKey{Name: cloudProfileName}, gomock.AssignableToTypeOf(&gardencorev1beta1.CloudProfile{})).DoAndReturn(func(_ context.Context, _ client.ObjectKey, obj *gardencorev1beta1.CloudProfile, _ ...client.GetOption) error { + *obj = *cloudProfile + return nil + }) + + want := cloudProfile.DeepCopy() + want.Status = wantStatus + + c.EXPECT().Status().Return(status) + status.EXPECT().Update(gomock.Any(), gomock.AssignableToTypeOf(&gardencorev1beta1.CloudProfile{})).Do(func(_ context.Context, obj client.Object, _ ...client.UpdateOption) { + Expect(obj).To(Equal(want)) + }) + + result, err := reconciler.Reconcile(ctx, reconcile.Request{NamespacedName: types.NamespacedName{Name: cloudProfileName}}) + Expect(result).To(Equal(reconcile.Result{})) + Expect(err).NotTo(HaveOccurred()) + } + ) + + It("should reconcile status of lifecycle classifications", func() { + var ( + now = time.Now() + + spec = gardencorev1beta1.CloudProfileSpec{ + Kubernetes: gardencorev1beta1.KubernetesSettings{ + Versions: []gardencorev1beta1.ExpirableVersion{ + { + Version: "1.28.2", + Lifecycle: []gardencorev1beta1.LifecycleStage{ + { + Classification: gardencorev1beta1.ClassificationPreview, + StartTime: ptr.To(metav1.NewTime(now.Add(-1 * time.Hour))), + }, + { + Classification: gardencorev1beta1.ClassificationSupported, + StartTime: ptr.To(metav1.NewTime(now.Add(3 * time.Hour))), + }, + }, + }, + }, + }, + } + + wantStatus = gardencorev1beta1.CloudProfileStatus{ + KubernetesVersions: []gardencorev1beta1.ExpirableVersionStatus{ + { + Version: "1.28.2", + ClassificationState: gardencorev1beta1.ClassificationPreview, + }, + }, + } + ) + + testStatus(spec, wantStatus) + }) + }) }) diff --git a/pkg/controllermanager/controller/namespacedcloudprofile/reconciler.go b/pkg/controllermanager/controller/namespacedcloudprofile/reconciler.go index 5b9e4a07902..0559b348da8 100644 --- a/pkg/controllermanager/controller/namespacedcloudprofile/reconciler.go +++ b/pkg/controllermanager/controller/namespacedcloudprofile/reconciler.go @@ -7,6 +7,7 @@ package namespacedcloudprofile import ( "context" "fmt" + "slices" "golang.org/x/exp/maps" corev1 "k8s.io/api/core/v1" @@ -116,7 +117,7 @@ func MergeCloudProfiles(namespacedCloudProfile *gardencorev1beta1.NamespacedClou namespacedCloudProfile.Status.CloudProfileSpec = cloudProfile.Spec if namespacedCloudProfile.Spec.Kubernetes != nil { - namespacedCloudProfile.Status.CloudProfileSpec.Kubernetes.Versions = mergeDeep(namespacedCloudProfile.Status.CloudProfileSpec.Kubernetes.Versions, namespacedCloudProfile.Spec.Kubernetes.Versions, expirableVersionKeyFunc, mergeExpirationDates, false) + namespacedCloudProfile.Status.CloudProfileSpec.Kubernetes.Versions = mergeDeep(namespacedCloudProfile.Status.CloudProfileSpec.Kubernetes.Versions, namespacedCloudProfile.Spec.Kubernetes.Versions, expirableVersionKeyFunc, mergeExpirableVersions, false) } namespacedCloudProfile.Status.CloudProfileSpec.MachineImages = mergeDeep(namespacedCloudProfile.Status.CloudProfileSpec.MachineImages, namespacedCloudProfile.Spec.MachineImages, machineImageKeyFunc, mergeMachineImages, true) namespacedCloudProfile.Status.CloudProfileSpec.MachineTypes = mergeDeep(namespacedCloudProfile.Status.CloudProfileSpec.MachineTypes, namespacedCloudProfile.Spec.MachineTypes, machineTypeKeyFunc, nil, true) @@ -128,24 +129,101 @@ func MergeCloudProfiles(namespacedCloudProfile *gardencorev1beta1.NamespacedClou } var ( - expirableVersionKeyFunc = func(v gardencorev1beta1.ExpirableVersion) string { return v.Version } - machineImageKeyFunc = func(i gardencorev1beta1.MachineImage) string { return i.Name } - machineImageVersionKeyFunc = func(v gardencorev1beta1.MachineImageVersion) string { return v.Version } - machineTypeKeyFunc = func(t gardencorev1beta1.MachineType) string { return t.Name } + expirableVersionKeyFunc = func(v gardencorev1beta1.ExpirableVersion) string { return v.Version } + classificationLifecycleKeyFunc = func(c gardencorev1beta1.LifecycleStage) string { return string(c.Classification) } + machineImageKeyFunc = func(i gardencorev1beta1.MachineImage) string { return i.Name } + machineImageVersionKeyFunc = func(v gardencorev1beta1.MachineImageVersion) string { return v.Version } + machineTypeKeyFunc = func(t gardencorev1beta1.MachineType) string { return t.Name } ) -func mergeExpirationDates(base, override gardencorev1beta1.ExpirableVersion) gardencorev1beta1.ExpirableVersion { - base.ExpirationDate = override.ExpirationDate +func mergeExpirableVersions(base, override gardencorev1beta1.ExpirableVersion) gardencorev1beta1.ExpirableVersion { + migratedBase := migrateExpirableVersionToLifecycle(base) + migratedOverride := migrateExpirableVersionToLifecycle(override) + + migratedBase.Lifecycle = mergeDeep(migratedBase.Lifecycle, migratedOverride.Lifecycle, classificationLifecycleKeyFunc, mergeClassificationLifecycles, false) + + order := map[gardencorev1beta1.VersionClassification]int{ + gardencorev1beta1.ClassificationUnavailable: 0, + gardencorev1beta1.ClassificationPreview: 1, + gardencorev1beta1.ClassificationSupported: 2, + gardencorev1beta1.ClassificationDeprecated: 3, + gardencorev1beta1.ClassificationExpired: 4, + } + compareFunc := func(a, b gardencorev1beta1.LifecycleStage) int { + return order[a.Classification] - order[b.Classification] + } + slices.SortFunc(migratedBase.Lifecycle, compareFunc) + + for _, overrideStage := range migratedOverride.Lifecycle { + // Push startTimes of all subsequent classifications after last custom version + for i, baseStage := range migratedBase.Lifecycle { + if compareFunc(baseStage, overrideStage) < 0 && + (baseStage.StartTime != nil && overrideStage.StartTime.Before(baseStage.StartTime)) { + migratedBase.Lifecycle[i].StartTime = overrideStage.StartTime + } + + if compareFunc(baseStage, overrideStage) > 0 && + (baseStage.StartTime == nil || baseStage.StartTime.Before(overrideStage.StartTime)) { + migratedBase.Lifecycle[i].StartTime = overrideStage.StartTime + } + } + } + + return migratedBase +} + +func mergeClassificationLifecycles(base, override gardencorev1beta1.LifecycleStage) gardencorev1beta1.LifecycleStage { + base.StartTime = override.StartTime return base } +func migrateExpirableVersionToLifecycle(version gardencorev1beta1.ExpirableVersion) gardencorev1beta1.ExpirableVersion { + var result = version.DeepCopy() + + if result.Classification != nil || result.ExpirationDate != nil { + // old cloud profile definition, convert to lifecycle + // this can be removed as soon as we remove the old classification and expiration date fields + + if result.Classification != nil { + result.Lifecycle = append(result.Lifecycle, gardencorev1beta1.LifecycleStage{ + Classification: *result.Classification, + }) + } + + if result.ExpirationDate != nil { + if result.Classification == nil { + result.Lifecycle = append(result.Lifecycle, gardencorev1beta1.LifecycleStage{ + Classification: gardencorev1beta1.ClassificationSupported, + }) + } + + result.Lifecycle = append(result.Lifecycle, gardencorev1beta1.LifecycleStage{ + Classification: gardencorev1beta1.ClassificationExpired, + StartTime: result.ExpirationDate, + }) + } + } + + if len(result.Lifecycle) == 0 { + // when there is no classification lifecycle defined then default to supported + result.Lifecycle = append(result.Lifecycle, gardencorev1beta1.LifecycleStage{ + Classification: gardencorev1beta1.ClassificationSupported, + }) + } + + result.Classification = nil + result.ExpirationDate = nil + + return *result +} + func mergeMachineImages(base, override gardencorev1beta1.MachineImage) gardencorev1beta1.MachineImage { base.Versions = mergeDeep(base.Versions, override.Versions, machineImageVersionKeyFunc, mergeMachineImageVersions, true) return base } func mergeMachineImageVersions(base, override gardencorev1beta1.MachineImageVersion) gardencorev1beta1.MachineImageVersion { - base.ExpirableVersion = mergeExpirationDates(base.ExpirableVersion, override.ExpirableVersion) + base.ExpirableVersion = mergeExpirableVersions(base.ExpirableVersion, override.ExpirableVersion) return base } diff --git a/pkg/controllermanager/controller/namespacedcloudprofile/reconciler_test.go b/pkg/controllermanager/controller/namespacedcloudprofile/reconciler_test.go index 69e7db13c73..c2c958f0c64 100644 --- a/pkg/controllermanager/controller/namespacedcloudprofile/reconciler_test.go +++ b/pkg/controllermanager/controller/namespacedcloudprofile/reconciler_test.go @@ -203,7 +203,7 @@ var _ = Describe("NamespacedCloudProfile Reconciler", func() { Expect(err).ToNot(HaveOccurred()) }) - It("should merge Kubernetes versions correctly", func() { + It("should ignore ExpirationDate set only in NamespacedCloudProfile", func() { namespacedCloudProfile.Spec.Kubernetes.Versions = []gardencorev1beta1.ExpirableVersion{ {Version: "1.0.0", ExpirationDate: &newExpiryDate}, } @@ -221,7 +221,152 @@ var _ = Describe("NamespacedCloudProfile Reconciler", func() { c.EXPECT().Patch(gomock.Any(), gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{}), gomock.Any()) c.EXPECT().Patch(gomock.Any(), gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{}), gomock.Any()).DoAndReturn(func(_ context.Context, o client.Object, patch client.Patch, _ ...client.PatchOption) error { - Expect(patch.Data(o)).To(BeEquivalentTo(fmt.Sprintf(`{"status":{"cloudProfileSpec":{"kubernetes":{"versions":[{"expirationDate":"%s","version":"1.0.0"}]},"machineImages":[],"machineTypes":[]}}}`, newExpiryDate.UTC().Format(time.RFC3339)))) + Expect(patch.Data(o)).To(BeEquivalentTo(`{"status":{"cloudProfileSpec":{"kubernetes":{"versions":[{"lifecycle":[{"classification":"supported"}],"version":"1.0.0"}]},"machineImages":[],"machineTypes":[]}}}`)) + return nil + }) + + result, err := reconciler.Reconcile(ctx, reconcile.Request{NamespacedName: types.NamespacedName{Name: namespacedCloudProfileName, Namespace: namespaceName}}) + Expect(result).To(Equal(reconcile.Result{})) + Expect(err).ToNot(HaveOccurred()) + }) + + It("should merge Kubernetes versions ExpirationDates correctly", func() { + cloudProfile.Spec.Kubernetes.Versions = []gardencorev1beta1.ExpirableVersion{ + {Version: "1.0.0", ExpirationDate: ptr.To(metav1.Time{Time: newExpiryDate.Add(24 * time.Hour)})}, + } + namespacedCloudProfile.Spec.Kubernetes.Versions = []gardencorev1beta1.ExpirableVersion{ + {Version: "1.0.0", ExpirationDate: &newExpiryDate}, + } + + c.EXPECT().Get(gomock.Any(), client.ObjectKey{Name: namespacedCloudProfileName, Namespace: namespaceName}, gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{})).DoAndReturn(func(_ context.Context, _ client.ObjectKey, obj *gardencorev1beta1.NamespacedCloudProfile, _ ...client.GetOption) error { + namespacedCloudProfile.DeepCopyInto(obj) + return nil + }) + + c.EXPECT().Get(gomock.Any(), client.ObjectKey{Name: cloudProfileName}, gomock.AssignableToTypeOf(&gardencorev1beta1.CloudProfile{})).DoAndReturn(func(_ context.Context, _ client.ObjectKey, obj *gardencorev1beta1.CloudProfile, _ ...client.GetOption) error { + cloudProfile.DeepCopyInto(obj) + return nil + }) + + c.EXPECT().Patch(gomock.Any(), gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{}), gomock.Any()) + + c.EXPECT().Patch(gomock.Any(), gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{}), gomock.Any()).DoAndReturn(func(_ context.Context, o client.Object, patch client.Patch, _ ...client.PatchOption) error { + Expect(patch.Data(o)).To(BeEquivalentTo(fmt.Sprintf(`{"status":{"cloudProfileSpec":{"kubernetes":{"versions":[{"lifecycle":[{"classification":"supported"},{"classification":"expired","startTime":"%s"}],"version":"1.0.0"}]},"machineImages":[],"machineTypes":[]}}}`, newExpiryDate.UTC().Format(time.RFC3339)))) + return nil + }) + + result, err := reconciler.Reconcile(ctx, reconcile.Request{NamespacedName: types.NamespacedName{Name: namespacedCloudProfileName, Namespace: namespaceName}}) + Expect(result).To(Equal(reconcile.Result{})) + Expect(err).ToNot(HaveOccurred()) + }) + + It("should ignore Lifecycles expired classification set only in NamespacedCloudProfile", func() { + namespacedCloudProfile.Spec.Kubernetes.Versions = []gardencorev1beta1.ExpirableVersion{ + {Version: "1.0.0", Lifecycle: []gardencorev1beta1.LifecycleStage{ + { + Classification: gardencorev1beta1.ClassificationExpired, + StartTime: &newExpiryDate, + }, + }}, + } + + c.EXPECT().Get(gomock.Any(), client.ObjectKey{Name: namespacedCloudProfileName, Namespace: namespaceName}, gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{})).DoAndReturn(func(_ context.Context, _ client.ObjectKey, obj *gardencorev1beta1.NamespacedCloudProfile, _ ...client.GetOption) error { + namespacedCloudProfile.DeepCopyInto(obj) + return nil + }) + + c.EXPECT().Get(gomock.Any(), client.ObjectKey{Name: cloudProfileName}, gomock.AssignableToTypeOf(&gardencorev1beta1.CloudProfile{})).DoAndReturn(func(_ context.Context, _ client.ObjectKey, obj *gardencorev1beta1.CloudProfile, _ ...client.GetOption) error { + cloudProfile.DeepCopyInto(obj) + return nil + }) + + c.EXPECT().Patch(gomock.Any(), gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{}), gomock.Any()) + + c.EXPECT().Patch(gomock.Any(), gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{}), gomock.Any()).DoAndReturn(func(_ context.Context, o client.Object, patch client.Patch, _ ...client.PatchOption) error { + Expect(patch.Data(o)).To(BeEquivalentTo(`{"status":{"cloudProfileSpec":{"kubernetes":{"versions":[{"lifecycle":[{"classification":"supported"}],"version":"1.0.0"}]},"machineImages":[],"machineTypes":[]}}}`)) + return nil + }) + + result, err := reconciler.Reconcile(ctx, reconcile.Request{NamespacedName: types.NamespacedName{Name: namespacedCloudProfileName, Namespace: namespaceName}}) + Expect(result).To(Equal(reconcile.Result{})) + Expect(err).ToNot(HaveOccurred()) + }) + + It("should adjust supported startTime to deprecrated startTime when before", func() { + overriddenDeprecatedDate := &metav1.Time{Time: time.Now()} + supportedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 1)} + deprecatedDate := &metav1.Time{Time: time.Now().AddDate(0, 0, 2)} + cloudProfile.Spec.Kubernetes.Versions = []gardencorev1beta1.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []gardencorev1beta1.LifecycleStage{ + {Classification: gardencorev1beta1.ClassificationPreview}, + {Classification: gardencorev1beta1.ClassificationSupported, StartTime: supportedDate}, + {Classification: gardencorev1beta1.ClassificationDeprecated, StartTime: deprecatedDate}, + }, + }, + } + namespacedCloudProfile.Spec.Kubernetes.Versions = []gardencorev1beta1.ExpirableVersion{ + { + Version: "1.1.0", + Lifecycle: []gardencorev1beta1.LifecycleStage{ + {Classification: gardencorev1beta1.ClassificationDeprecated, StartTime: overriddenDeprecatedDate}, + }, + }, + } + + namespacedcloudprofilecontroller.MergeCloudProfiles(namespacedCloudProfile, cloudProfile) + + Expect(namespacedCloudProfile.Status.CloudProfileSpec.Kubernetes.Versions[0].Lifecycle).To(Equal([]gardencorev1beta1.LifecycleStage{ + {Classification: gardencorev1beta1.ClassificationPreview}, + {Classification: gardencorev1beta1.ClassificationSupported, StartTime: overriddenDeprecatedDate}, + {Classification: gardencorev1beta1.ClassificationDeprecated, StartTime: overriddenDeprecatedDate}, + })) + }) + + It("should merge Kubernetes version Lifecycles classification startTimes correctly", func() { + cloudProfile.Spec.Kubernetes.Versions = []gardencorev1beta1.ExpirableVersion{ + {Version: "1.0.0", Lifecycle: []gardencorev1beta1.LifecycleStage{ + { + Classification: gardencorev1beta1.ClassificationSupported, + }, + { + Classification: gardencorev1beta1.ClassificationDeprecated, + StartTime: ptr.To(metav1.Time{Time: newExpiryDate.Add(12 * time.Hour)}), + }, + { + Classification: gardencorev1beta1.ClassificationExpired, + StartTime: ptr.To(metav1.Time{Time: newExpiryDate.Add(24 * time.Hour)}), + }, + }}, + } + namespacedCloudProfile.Spec.Kubernetes.Versions = []gardencorev1beta1.ExpirableVersion{ + {Version: "1.0.0", Lifecycle: []gardencorev1beta1.LifecycleStage{ + { + Classification: gardencorev1beta1.ClassificationDeprecated, + StartTime: ptr.To(metav1.Time{Time: newExpiryDate.Add(48 * time.Hour)}), + }, + }}, + } + + c.EXPECT().Get(gomock.Any(), client.ObjectKey{Name: namespacedCloudProfileName, Namespace: namespaceName}, gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{})).DoAndReturn(func(_ context.Context, _ client.ObjectKey, obj *gardencorev1beta1.NamespacedCloudProfile, _ ...client.GetOption) error { + namespacedCloudProfile.DeepCopyInto(obj) + return nil + }) + + c.EXPECT().Get(gomock.Any(), client.ObjectKey{Name: cloudProfileName}, gomock.AssignableToTypeOf(&gardencorev1beta1.CloudProfile{})).DoAndReturn(func(_ context.Context, _ client.ObjectKey, obj *gardencorev1beta1.CloudProfile, _ ...client.GetOption) error { + cloudProfile.DeepCopyInto(obj) + return nil + }) + + c.EXPECT().Patch(gomock.Any(), gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{}), gomock.Any()) + + c.EXPECT().Patch(gomock.Any(), gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{}), gomock.Any()).DoAndReturn(func(_ context.Context, o client.Object, patch client.Patch, _ ...client.PatchOption) error { + Expect(patch.Data(o)).To(BeEquivalentTo(fmt.Sprintf( + `{"status":{"cloudProfileSpec":{"kubernetes":{"versions":[{"lifecycle":[{"classification":"supported"},{"classification":"deprecated","startTime":"%s"},{"classification":"expired","startTime":"%s"}],"version":"1.0.0"}]},"machineImages":[],"machineTypes":[]}}}`, + newExpiryDate.UTC().Add(48*time.Hour).Format(time.RFC3339), // deprecated: taken from NamespacedCloudProfile Spec + newExpiryDate.UTC().Add(48*time.Hour).Format(time.RFC3339), // expired: is postponed to the deprecated date + ))) return nil }) @@ -431,7 +576,9 @@ var _ = Describe("NamespacedCloudProfile Reconciler", func() { Expect(err).ToNot(HaveOccurred()) }) - It("should merge MachineImages correctly", func() { + // TODO: Add the following test also with classification lifecycle set: + + It("should merge MachineImages correctly and ignore an additional ExpirationDate set", func() { newExpiryDate := metav1.Now() namespacedCloudProfile.Spec.MachineImages = []gardencorev1beta1.MachineImage{ { @@ -458,7 +605,7 @@ var _ = Describe("NamespacedCloudProfile Reconciler", func() { }) c.EXPECT().Patch(gomock.Any(), gomock.AssignableToTypeOf(&gardencorev1beta1.NamespacedCloudProfile{}), gomock.Any()).DoAndReturn(func(_ context.Context, o client.Object, patch client.Patch, _ ...client.PatchOption) error { - versionOverride := fmt.Sprintf(`{"architectures":["amd64"],"cri":[{"name":"containerd"}],"expirationDate":"%s","kubeletVersionConstraint":"==1.30.0","version":"1.0.0"}`, newExpiryDate.UTC().Format(time.RFC3339)) + versionOverride := `{"architectures":["amd64"],"cri":[{"name":"containerd"}],"kubeletVersionConstraint":"==1.30.0","lifecycle":[{"classification":"supported"}],"version":"1.0.0"}` versionAdded := `{"version":"1.1.2"}` Expect(patch.Data(o)).To(And( // The order is (currently) indeterministic. diff --git a/pkg/controllermanager/controller/shoot/maintenance/reconciler.go b/pkg/controllermanager/controller/shoot/maintenance/reconciler.go index c1a7533f7c6..8fdb0ab8494 100644 --- a/pkg/controllermanager/controller/shoot/maintenance/reconciler.go +++ b/pkg/controllermanager/controller/shoot/maintenance/reconciler.go @@ -642,7 +642,7 @@ func shouldKubernetesVersionBeUpdated(kubernetesVersion string, autoUpdate bool, return true, updateReason, true, nil } - if ExpirationDateExpired(version.ExpirationDate) { + if v1beta1helper.VersionIsExpired(version) { updateReason = "Kubernetes version expired - force update required" return true, updateReason, true, nil } @@ -800,7 +800,7 @@ func shouldMachineImageVersionBeUpdated(shootMachineImage *gardencorev1beta1.Sho return true, updateReason, true } - if ExpirationDateExpired(machineImage.Versions[versionIndex].ExpirationDate) { + if v1beta1helper.VersionIsExpired(machineImage.Versions[versionIndex].ExpirableVersion) { updateReason = fmt.Sprintf("Machine image version expired - force update required (image update strategy: %s)", *machineImage.UpdateStrategy) return true, updateReason, true } @@ -886,14 +886,6 @@ func determineVersionForStrategy(expirableVersions []gardencorev1beta1.Expirable return versionForForceUpdate, nil } -// ExpirationDateExpired returns if now is equal or after the given expirationDate -func ExpirationDateExpired(timestamp *metav1.Time) bool { - if timestamp == nil { - return false - } - return time.Now().UTC().After(timestamp.Time) || time.Now().UTC().Equal(timestamp.Time) -} - // ensureSufficientMaxWorkers ensures that the number of max workers of a worker group is greater or equal to its number of zones func ensureSufficientMaxWorkers(shoot *gardencorev1beta1.Shoot, reason string) []string { var reasonsForUpdate []string diff --git a/pkg/controllermanager/controller/shoot/maintenance/reconciler_test.go b/pkg/controllermanager/controller/shoot/maintenance/reconciler_test.go index 431bae24d6f..9b676baf623 100644 --- a/pkg/controllermanager/controller/shoot/maintenance/reconciler_test.go +++ b/pkg/controllermanager/controller/shoot/maintenance/reconciler_test.go @@ -36,20 +36,6 @@ var _ = Describe("Shoot Maintenance", func() { expirationDateInThePast = metav1.Time{Time: now.AddDate(0, 0, -1)} }) - Context("Shoot Maintenance", func() { - Describe("#ExpirationDateExpired", func() { - It("should determine that expirationDate applies", func() { - applies := ExpirationDateExpired(&expirationDateInThePast) - Expect(applies).To(BeTrue()) - }) - - It("should determine that expirationDate not applies", func() { - applies := ExpirationDateExpired(&expirationDateInTheFuture) - Expect(applies).To(BeFalse()) - }) - }) - }) - Describe("#maintainMachineImages", func() { var ( shootCurrentImage *gardencorev1beta1.ShootMachineImage diff --git a/plugin/pkg/global/resourcereferencemanager/admission.go b/plugin/pkg/global/resourcereferencemanager/admission.go index 93b69d9a730..18f6a8fa047 100644 --- a/plugin/pkg/global/resourcereferencemanager/admission.go +++ b/plugin/pkg/global/resourcereferencemanager/admission.go @@ -10,6 +10,7 @@ import ( "fmt" "io" "reflect" + "slices" "strings" "sync" "time" @@ -38,6 +39,7 @@ import ( "github.com/gardener/gardener/pkg/apis/core/helper" gardencorev1beta1 "github.com/gardener/gardener/pkg/apis/core/v1beta1" v1beta1constants "github.com/gardener/gardener/pkg/apis/core/v1beta1/constants" + v1beta1helper "github.com/gardener/gardener/pkg/apis/core/v1beta1/helper" "github.com/gardener/gardener/pkg/apis/security" securityv1alpha1 "github.com/gardener/gardener/pkg/apis/security/v1alpha1" "github.com/gardener/gardener/pkg/apis/seedmanagement" @@ -492,13 +494,31 @@ func (r *ReferenceManager) Admit(ctx context.Context, a admission.Attributes, _ return apierrors.NewBadRequest("could not convert old resource into CloudProfile object") } + kubernetesKeyFunc := func(v core.ExpirableVersion) string { return v.Version } + newKubernetesVersions := gardenerutils.CreateMapFromSlice(cloudProfile.Spec.Kubernetes.Versions, kubernetesKeyFunc) + // getting Kubernetes versions that have been removed from the CloudProfile removedKubernetesVersions := sets.StringKeySet(helper.GetRemovedVersions(oldCloudProfile.Spec.Kubernetes.Versions, cloudProfile.Spec.Kubernetes.Versions)) + removedKubernetesClassificationLifecycles := make(map[string][]core.VersionClassification) + + for _, existingVersion := range oldCloudProfile.Spec.Kubernetes.Versions { + if removedKubernetesVersions.Has(existingVersion.Version) { + continue + } + for _, existingLifecycleClass := range existingVersion.Lifecycle { + if slices.ContainsFunc(newKubernetesVersions[existingVersion.Version].Lifecycle, func(newLifecycle core.LifecycleStage) bool { + return newLifecycle.Classification == existingLifecycleClass.Classification + }) { + continue + } + removedKubernetesClassificationLifecycles[existingVersion.Version] = append(removedKubernetesClassificationLifecycles[existingVersion.Version], existingLifecycleClass.Classification) + } + } // getting Machine image versions that have been removed from or added to the CloudProfile - removedMachineImages, removedMachineImageVersions, addedMachineImages, addedMachineImageVersions := helper.GetMachineImageDiff(oldCloudProfile.Spec.MachineImages, cloudProfile.Spec.MachineImages) + diff := helper.GetMachineImageDiff(oldCloudProfile.Spec.MachineImages, cloudProfile.Spec.MachineImages) - if len(removedKubernetesVersions) > 0 || len(removedMachineImageVersions) > 0 || len(addedMachineImageVersions) > 0 { + if len(removedKubernetesVersions) > 0 || len(diff.RemovedVersions) > 0 || len(diff.AddedVersions) > 0 || len(diff.RemovedVersionClassifications) > 0 || len(removedKubernetesClassificationLifecycles) > 0 { shootList, err1 := r.shootLister.List(labels.Everything()) if err1 != nil { return apierrors.NewInternalError(fmt.Errorf("could not list shoots to verify that Kubernetes and/or Machine image version can be removed: %v", err1)) @@ -529,6 +549,12 @@ func (r *ReferenceManager) Admit(ctx context.Context, a admission.Attributes, _ ncpNamespacedName := types.NamespacedName{Name: ncp.Name, Namespace: ncp.Namespace} relevantNamespacedCloudProfiles[ncpNamespacedName.String()] = ncp + matchesClassification := func(classification core.VersionClassification) func(stage gardencorev1beta1.LifecycleStage) bool { + return func(stage gardencorev1beta1.LifecycleStage) bool { + return core.VersionClassification(stage.Classification) == classification + } + } + go func(nscpfl *gardencorev1beta1.NamespacedCloudProfile) { defer wg.Done() @@ -537,21 +563,37 @@ func (r *ReferenceManager) Admit(ctx context.Context, a admission.Attributes, _ if removedKubernetesVersions.Has(kubernetesVersion.Version) { channel <- fmt.Errorf("unable to delete Kubernetes version %q from CloudProfile %q - version is still in use by NamespacedCloudProfile '%s/%s'", kubernetesVersion.Version, cloudProfile.Name, nscpfl.Namespace, nscpfl.Name) } + if removedClassifications, exists := removedKubernetesClassificationLifecycles[kubernetesVersion.Version]; exists { + for _, c := range removedClassifications { + if slices.ContainsFunc(kubernetesVersion.Lifecycle, matchesClassification(c)) { + channel <- fmt.Errorf("unable to delete Kubernetes classification lifecycle %q from version %q from CloudProfile %q still in use by NamespacedCloudProfile '%s/%s'", c, kubernetesVersion.Version, cloudProfile.Name, nscpfl.Namespace, nscpfl.Name) + } + } + } } } for _, machineImage := range nscpfl.Spec.MachineImages { - if removedMachineImages.Has(machineImage.Name) { + if diff.RemovedImages.Has(machineImage.Name) { channel <- fmt.Errorf("unable to delete MachineImage %q from CloudProfile %q - MachineImage is still in use by NamespacedCloudProfile %q", machineImage.Name, cloudProfile.Name, ncpNamespacedName.String()) } - if addedMachineImages.Has(machineImage.Name) { + if diff.AddedImages.Has(machineImage.Name) { channel <- fmt.Errorf("unable to add MachineImage %q to CloudProfile %q - MachineImage is already defined by NamespacedCloudProfile %q", machineImage.Name, cloudProfile.Name, ncpNamespacedName.String()) } - if removedVersions, exists := removedMachineImageVersions[machineImage.Name]; exists { - for _, imageVersion := range machineImage.Versions { + for _, imageVersion := range machineImage.Versions { + if removedVersions, exists := diff.RemovedVersions[machineImage.Name]; exists { if removedVersions.Has(imageVersion.Version) { channel <- fmt.Errorf("unable to delete MachineImage version '%s/%s' from CloudProfile %q - version is still in use by NamespacedCloudProfile '%s/%s'", machineImage.Name, imageVersion.Version, cloudProfile.Name, nscpfl.Namespace, nscpfl.Name) } + + } + if removedClassifications, exists := diff.RemovedVersionClassifications[machineImage.Name]; exists { + for _, c := range removedClassifications[imageVersion.Version] { + if slices.ContainsFunc(imageVersion.Lifecycle, matchesClassification(c)) { + channel <- fmt.Errorf("unable to delete classification lifecycle %q from MachineImage version '%s/%s' from CloudProfile %q still in use by NamespacedCloudProfile '%s/%s'", c, machineImage.Name, imageVersion.Version, cloudProfile.Name, nscpfl.Namespace, nscpfl.Name) + } + + } } } } @@ -577,11 +619,11 @@ func (r *ReferenceManager) Admit(ctx context.Context, a admission.Attributes, _ continue } // happens if Shoot runs an image that does not exist in the old CloudProfile - in this case: ignore - if _, ok := removedMachineImageVersions[worker.Machine.Image.Name]; !ok { + if _, ok := diff.RemovedVersions[worker.Machine.Image.Name]; !ok { continue } - if removedMachineImageVersions[worker.Machine.Image.Name].Has(*worker.Machine.Image.Version) { + if diff.RemovedVersions[worker.Machine.Image.Name].Has(*worker.Machine.Image.Version) { channel <- fmt.Errorf("unable to delete Machine image version '%s/%s' from CloudProfile %q - version is still in use by shoot '%s/%s' by worker %q", worker.Machine.Image.Name, *worker.Machine.Image.Version, cloudProfile.Name, shoot.Namespace, shoot.Name, worker.Name) } } @@ -1146,7 +1188,7 @@ func getRemovedMachineImageVersions(namespacedCloudProfile, oldNamespacedCloudPr func validateShootForRemovedKubernetesVersions(channel chan error, shoot *gardencorev1beta1.Shoot, removedKubernetesVersions sets.Set[string], parentCloudProfileKubernetesVersions map[string]gardencorev1beta1.ExpirableVersion, namespacedCloudProfile *core.NamespacedCloudProfile) { shootKubernetesVersion := shoot.Spec.Kubernetes.Version if removedKubernetesVersions.Has(shootKubernetesVersion) { - if parentCloudProfileKubernetesVersions[shootKubernetesVersion].ExpirationDate != nil && parentCloudProfileKubernetesVersions[shootKubernetesVersion].ExpirationDate.Before(&metav1.Time{Time: time.Now()}) { + if v1beta1helper.VersionIsExpired(parentCloudProfileKubernetesVersions[shootKubernetesVersion]) { channel <- fmt.Errorf("unable to delete Kubernetes version %q from NamespacedCloudProfile '%s/%s' - version with extended expiration date is still in use by shoot '%s/%s'", shootKubernetesVersion, namespacedCloudProfile.Namespace, namespacedCloudProfile.Name, shoot.Namespace, shoot.Name) } } @@ -1165,7 +1207,7 @@ func validateShootWorkersForRemovedMachineImageVersions(channel chan error, shoo if removedMachineImageVersions[worker.Machine.Image.Name].Has(*worker.Machine.Image.Version) { parentVersion, exists := parentCloudProfileMachineImageVersions[worker.Machine.Image.Name][*worker.Machine.Image.Version] - if !exists || parentVersion.ExpirationDate != nil && parentVersion.ExpirationDate.Before(&metav1.Time{Time: time.Now()}) { + if !exists || v1beta1helper.VersionIsExpired(parentVersion.ExpirableVersion) { channel <- fmt.Errorf("unable to delete Machine image version '%s/%s' from NamespacedCloudProfile '%s/%s' - version is still in use by shoot '%s/%s' by worker %q", worker.Machine.Image.Name, *worker.Machine.Image.Version, namespacedCloudProfile.Namespace, namespacedCloudProfile.Name, shoot.Namespace, shoot.Name, worker.Name) } } diff --git a/plugin/pkg/global/resourcereferencemanager/admission_test.go b/plugin/pkg/global/resourcereferencemanager/admission_test.go index 8a14efc1094..5040d76a13d 100644 --- a/plugin/pkg/global/resourcereferencemanager/admission_test.go +++ b/plugin/pkg/global/resourcereferencemanager/admission_test.go @@ -1847,6 +1847,40 @@ var _ = Describe("resourcereferencemanager", func() { ))) }) + It("should reject removal of kubernetes version classification lifecycle that are still in use by a NamespacedCloudProfile", func() { + namespacedCloudProfile := &gardencorev1beta1.NamespacedCloudProfile{ + Spec: gardencorev1beta1.NamespacedCloudProfileSpec{ + Parent: gardencorev1beta1.CloudProfileReference{Kind: "CloudProfile", Name: cloudProfile.Name}, + Kubernetes: &gardencorev1beta1.KubernetesSettings{Versions: []gardencorev1beta1.ExpirableVersion{ + {Version: "1.24.1", Lifecycle: []gardencorev1beta1.LifecycleStage{ + {Classification: gardencorev1beta1.ClassificationExpired, StartTime: ptr.To(metav1.Now())}, + }}, + }}, + }, + } + Expect(gardenCoreInformerFactory.Core().V1beta1().NamespacedCloudProfiles().Informer().GetStore().Add(namespacedCloudProfile)).To(Succeed()) + + cloudProfile.Spec.Kubernetes.Versions[1].Lifecycle = []core.LifecycleStage{ + {Classification: core.ClassificationSupported}, + {Classification: core.ClassificationExpired, StartTime: ptr.To(metav1.Now())}, + } + cloudProfileNew := cloudProfile.DeepCopy() + cloudProfileNew.Spec = core.CloudProfileSpec{ + Kubernetes: core.KubernetesSettings{ + Versions: []core.ExpirableVersion{ + {Version: "1.24.1", Lifecycle: []core.LifecycleStage{{Classification: core.ClassificationSupported}}}, + }, + }, + } + + attrs := admission.NewAttributesRecord(cloudProfileNew, &cloudProfile, core.Kind("CloudProfile").WithVersion("version"), "", cloudProfile.Name, core.Resource("CloudProfile").WithVersion("version"), "", admission.Update, &metav1.UpdateOptions{}, false, defaultUserInfo) + + Expect(admissionHandler.Admit(context.TODO(), attrs, nil)).To(MatchError(And( + ContainSubstring("unable to delete Kubernetes classification lifecycle \"expired\" from version \"1.24.1\""), + ContainSubstring("still in use by NamespacedCloudProfile"), + ))) + }) + It("should reject removal of kubernetes versions that are still in use by a Shoot referencing a NamespacedCloudProfile", func() { namespacedCloudProfile := &gardencorev1beta1.NamespacedCloudProfile{ Spec: gardencorev1beta1.NamespacedCloudProfileSpec{ diff --git a/plugin/pkg/namespacedcloudprofile/validator/admission_test.go b/plugin/pkg/namespacedcloudprofile/validator/admission_test.go index 750dfd5dea4..e43659e2967 100644 --- a/plugin/pkg/namespacedcloudprofile/validator/admission_test.go +++ b/plugin/pkg/namespacedcloudprofile/validator/admission_test.go @@ -127,6 +127,7 @@ var _ = Describe("Admission", func() { }) It("should fail if the latest Kubernetes version has an expiration date", func() { + parentCloudProfile.Spec.Kubernetes.Versions[0] = gardencorev1beta1.ExpirableVersion{Version: "1.30.0", Classification: ptr.To(gardencorev1beta1.ClassificationExpired)} Expect(coreInformerFactory.Core().V1beta1().CloudProfiles().Informer().GetStore().Add(parentCloudProfile)).To(Succeed()) namespacedCloudProfile.Spec.Kubernetes = &gardencore.KubernetesSettings{Versions: []gardencore.ExpirableVersion{ @@ -419,9 +420,9 @@ var _ = Describe("Admission", func() { machineTypesConstraint []gardencorev1beta1.MachineType volumeTypesConstraint []gardencorev1beta1.VolumeType - supportedClassification = gardencorev1beta1.ClassificationSupported - previewClassification = gardencorev1beta1.ClassificationPreview - deprecatedClassification = gardencorev1beta1.ClassificationDeprecated + supportedClassification = gardencorev1beta1.ClassificationSupported + previewClassification = gardencorev1beta1.ClassificationPreview + expiredClassification = gardencorev1beta1.ClassificationExpired ) BeforeEach(func() { @@ -532,7 +533,7 @@ var _ = Describe("Admission", func() { }, { Version: "1.2.0", - Classification: &deprecatedClassification, + Classification: &expiredClassification, }, } namespacedCloudProfile.Spec.Kubernetes.Versions = []gardencorev1beta1.ExpirableVersion{ @@ -542,7 +543,7 @@ var _ = Describe("Admission", func() { }, { Version: "1.2.0", - Classification: &deprecatedClassification, + Classification: &expiredClassification, ExpirationDate: expirationDate, }, } @@ -551,7 +552,7 @@ var _ = Describe("Admission", func() { Expect(errorList).To(ConsistOf(PointTo(MatchFields(IgnoreExtras, Fields{ "Type": Equal(field.ErrorTypeInvalid), - "Field": Equal("status.cloudProfileSpec.kubernetes.versions[].expirationDate"), + "Field": Equal("status.cloudProfileSpec.kubernetes.versions[].lifecycle"), })))) }) diff --git a/plugin/pkg/shoot/validator/admission.go b/plugin/pkg/shoot/validator/admission.go index 6e0d4fdf289..dcbb06ee4d2 100644 --- a/plugin/pkg/shoot/validator/admission.go +++ b/plugin/pkg/shoot/validator/admission.go @@ -1400,12 +1400,12 @@ func findLatestVersion(constraints []gardencorev1beta1.ExpirableVersion, major, var latestVersion *semver.Version for _, versionConstraint := range constraints { // ignore expired versions - if versionConstraint.ExpirationDate != nil && versionConstraint.ExpirationDate.Time.UTC().Before(time.Now().UTC()) { + if !v1beta1helper.VersionIsActive(versionConstraint) { continue } // filter preview versions for defaulting - if ptr.Deref(versionConstraint.Classification, "") == gardencorev1beta1.ClassificationPreview { + if v1beta1helper.VersionIsPreview(versionConstraint) { continue } @@ -1441,7 +1441,7 @@ func validateKubernetesVersionConstraints(a admission.Attributes, constraints [] // Disallow usage of an expired Kubernetes version on Shoot creation and new worker pool creation // Updating an existing worker to a higher (ensured by validation) expired Kubernetes version is necessary for consecutive maintenance force updates if a.GetOperation() == admission.Create || isNewWorkerPool { - if versionConstraint.ExpirationDate != nil && versionConstraint.ExpirationDate.Time.UTC().Before(time.Now().UTC()) { + if !v1beta1helper.VersionIsActive(versionConstraint) { continue } } @@ -1451,7 +1451,7 @@ func validateKubernetesVersionConstraints(a admission.Attributes, constraints [] } versionStr := versionConstraint.Version - if ptr.Deref(versionConstraint.Classification, "") == gardencorev1beta1.ClassificationPreview { + if v1beta1helper.VersionIsPreview(versionConstraint) { versionStr += " (preview)" } validValues = append(validValues, versionStr) @@ -1800,9 +1800,9 @@ func validateMachineImagesConstraints(a admission.Attributes, constraints []gard for _, machineVersion := range machineImage.Versions { machineImageVersion := fmt.Sprintf("%s:%s", machineImage.Name, machineVersion.Version) - if machineVersion.ExpirationDate == nil || machineVersion.ExpirationDate.Time.UTC().After(time.Now().UTC()) { + if v1beta1helper.VersionIsActive(machineVersion.ExpirableVersion) { activeMachineImageVersions.Insert(machineImageVersion) - } else if machineVersion.ExpirationDate != nil && machineVersion.ExpirationDate.Time.UTC().Before(time.Now().UTC()) && a.GetOperation() == admission.Update && !isNewWorkerPool { + } else if v1beta1helper.VersionIsExpired(machineVersion.ExpirableVersion) && a.GetOperation() == admission.Update && !isNewWorkerPool { // An already expired machine image version is a viable machine image version for the worker pool if-and-only-if: // - this is an update call (no new Shoot creation) // - updates an existing worker pool (not for a new worker pool) diff --git a/plugin/pkg/utils/cloudprofile.go b/plugin/pkg/utils/cloudprofile.go index 16f229d49b6..b2ccd29a7c8 100644 --- a/plugin/pkg/utils/cloudprofile.go +++ b/plugin/pkg/utils/cloudprofile.go @@ -99,13 +99,13 @@ func ValidateCloudProfileChanges(cloudProfileLister gardencorev1beta1listers.Clo // Check that the target cloud profile still supports the currently used machine types, machine images and volume types. // No need to check for Kubernetes versions, as the NamespacedCloudProfile could have only extended a version so with the next maintenance the Shoot will be updated to a supported version. - _, removedMachineImageVersions, _, _ := helper.GetMachineImageDiff(oldCloudProfileSpecCore.MachineImages, newCloudProfileSpecCore.MachineImages) + diff := helper.GetMachineImageDiff(oldCloudProfileSpecCore.MachineImages, newCloudProfileSpecCore.MachineImages) machineTypes := gardenerutils.CreateMapFromSlice(newCloudProfileSpec.MachineTypes, func(mt gardencorev1beta1.MachineType) string { return mt.Name }) volumeTypes := gardenerutils.CreateMapFromSlice(newCloudProfileSpec.VolumeTypes, func(vt gardencorev1beta1.VolumeType) string { return vt.Name }) for _, w := range newShoot.Spec.Provider.Workers { - if len(removedMachineImageVersions) > 0 && w.Machine.Image != nil { - if removedVersions, exists := removedMachineImageVersions[w.Machine.Image.Name]; exists { + if len(diff.RemovedVersions) > 0 && w.Machine.Image != nil { + if removedVersions, exists := diff.RemovedVersions[w.Machine.Image.Name]; exists { if removedVersions.Has(w.Machine.Image.Version) { return fmt.Errorf("newly referenced cloud profile does not contain the machine image version \"%s@%s\" currently in use by worker \"%s\"", w.Machine.Image.Name, w.Machine.Image.Version, w.Name) } diff --git a/test/integration/controllermanager/seed/lifecycle/lifecycle_suite_test.go b/test/integration/controllermanager/seed/lifecycle/lifecycle_suite_test.go index 0081716ea80..f48a8c4b508 100644 --- a/test/integration/controllermanager/seed/lifecycle/lifecycle_suite_test.go +++ b/test/integration/controllermanager/seed/lifecycle/lifecycle_suite_test.go @@ -38,7 +38,7 @@ import ( func TestLifecycle(t *testing.T) { RegisterFailHandler(Fail) - RunSpecs(t, "Test Integration ControllerManager Seed Lifecycle Suite") + RunSpecs(t, "Test Integration ControllerManager Seed Lifecycles Suite") } const ( diff --git a/test/integration/controllermanager/seed/lifecycle/lifecycle_test.go b/test/integration/controllermanager/seed/lifecycle/lifecycle_test.go index bd0a847bf78..84cb7d56b0a 100644 --- a/test/integration/controllermanager/seed/lifecycle/lifecycle_test.go +++ b/test/integration/controllermanager/seed/lifecycle/lifecycle_test.go @@ -20,7 +20,7 @@ import ( . "github.com/gardener/gardener/pkg/utils/test/matchers" ) -var _ = Describe("Seed Lifecycle controller tests", func() { +var _ = Describe("Seed Lifecycles controller tests", func() { var ( seed *gardencorev1beta1.Seed lease *coordinationv1.Lease