From c6392c9ffcd18174b226ff0adaf56de398ca5440 Mon Sep 17 00:00:00 2001 From: Brad Davidson Date: Tue, 8 Oct 2024 21:46:12 +0000 Subject: [PATCH] Fix issue that caused passwd file and psk to be regenerated when rotating CA certs Signed-off-by: Brad Davidson --- pkg/server/cert.go | 52 +++++++++++++++++++++++++--------------------- 1 file changed, 28 insertions(+), 24 deletions(-) diff --git a/pkg/server/cert.go b/pkg/server/cert.go index bde425196ea3..ea03a305dfd1 100644 --- a/pkg/server/cert.go +++ b/pkg/server/cert.go @@ -75,6 +75,10 @@ func caCertReplace(server *config.Control, buf io.ReadCloser, force bool) error return err } + if err := defaultBootstrap(server, tmpServer); err != nil { + return errors.Wrap(err, "failed to set default bootstrap values") + } + if err := validateBootstrap(server, tmpServer); err != nil { if !force { return errors.Wrap(err, "failed to validate new CA certificates and keys") @@ -85,27 +89,16 @@ func caCertReplace(server *config.Control, buf io.ReadCloser, force bool) error return cluster.Save(context.TODO(), tmpServer, true) } -// validateBootstrap checks the new certs and keys to ensure that the cluster would function properly were they to be used. -// - The new leaf CA certificates must be verifiable using the same root and intermediate certs as the current leaf CA certificates. -// - The new service account signing key bundle must include the currently active signing key. -func validateBootstrap(oldServer, newServer *config.Control) error { +// defaultBootstrap provides default values from the existing bootstrap fields +// if the value is not tagged for rotation, or the current value is empty. +func defaultBootstrap(oldServer, newServer *config.Control) error { errs := []error{} - // Use reflection to iterate over all of the bootstrap fields, checking files at each of the new paths. oldMeta := reflect.ValueOf(&oldServer.Runtime.ControlRuntimeBootstrap).Elem() newMeta := reflect.ValueOf(&newServer.Runtime.ControlRuntimeBootstrap).Elem() - fields := []reflect.StructField{} + // use the existing file if the new file does not exist or is empty for _, field := range reflect.VisibleFields(oldMeta.Type()) { - // Only handle bootstrap fields tagged for rotation - if field.Tag.Get("rotate") != "true" { - continue - } - fields = append(fields, field) - } - - // first pass: use the existing file if the new file does not exist or is empty - for _, field := range fields { newVal := newMeta.FieldByName(field.Name) info, err := os.Stat(newVal.String()) if err != nil && !errors.Is(err, fs.ErrNotExist) { @@ -113,20 +106,34 @@ func validateBootstrap(oldServer, newServer *config.Control) error { continue } - if info == nil || info.Size() == 0 { + if field.Tag.Get("rotate") != "true" || info == nil || info.Size() == 0 { if newVal.CanSet() { oldVal := oldMeta.FieldByName(field.Name) - logrus.Infof("certificate: %s not provided; using current value %s", field.Name, oldVal) + logrus.Infof("Using current data for %s: %s", field.Name, oldVal) newVal.Set(oldVal) } else { errs = append(errs, fmt.Errorf("cannot use current data for %s; field is not settable", field.Name)) } } - } + return merr.NewErrors(errs...) +} - // second pass: validate file contents - for _, field := range fields { +// validateBootstrap checks the new certs and keys to ensure that the cluster would function properly were they to be used. +// - The new leaf CA certificates must be verifiable using the same root and intermediate certs as the current leaf CA certificates. +// - The new service account signing key bundle must include the currently active signing key. +func validateBootstrap(oldServer, newServer *config.Control) error { + errs := []error{} + + // Use reflection to iterate over all of the bootstrap fields, checking files at each of the new paths. + oldMeta := reflect.ValueOf(&oldServer.Runtime.ControlRuntimeBootstrap).Elem() + newMeta := reflect.ValueOf(&newServer.Runtime.ControlRuntimeBootstrap).Elem() + + for _, field := range reflect.VisibleFields(oldMeta.Type()) { + // Only handle bootstrap fields tagged for rotation + if field.Tag.Get("rotate") != "true" { + continue + } oldVal := oldMeta.FieldByName(field.Name) newVal := newMeta.FieldByName(field.Name) @@ -150,10 +157,7 @@ func validateBootstrap(oldServer, newServer *config.Control) error { } } - if len(errs) > 0 { - return merr.NewErrors(errs...) - } - return nil + return merr.NewErrors(errs...) } func validateCA(oldCAPath, newCAPath string) error {