mirror of
https://github.com/edgelesssys/constellation.git
synced 2025-05-05 07:45:27 -04:00
config: add separate option for handling attestation parameters (#1623)
* Add attestation options to config * Add join-config migration path for clusters with old measurement format * Always create MAA provider for Azure SNP clusters * Remove confidential VM option from provider in favor of attestation options * cli: add config migrate command to handle config migration (#1678) --------- Signed-off-by: Daniel Weiße <dw@edgeless.systems>
This commit is contained in:
parent
6027b066e5
commit
d7a2ddd939
74 changed files with 1339 additions and 1282 deletions
|
@ -10,56 +10,27 @@ import (
|
|||
"crypto/sha256"
|
||||
"encoding/base64"
|
||||
"encoding/hex"
|
||||
"errors"
|
||||
"fmt"
|
||||
|
||||
"github.com/edgelesssys/constellation/v2/internal/atls"
|
||||
"github.com/edgelesssys/constellation/v2/internal/attestation/choose"
|
||||
"github.com/edgelesssys/constellation/v2/internal/attestation/measurements"
|
||||
"github.com/edgelesssys/constellation/v2/internal/config"
|
||||
"github.com/edgelesssys/constellation/v2/internal/variant"
|
||||
"github.com/spf13/cobra"
|
||||
)
|
||||
|
||||
// Validator validates Platform Configuration Registers (PCRs).
|
||||
type Validator struct {
|
||||
attestationVariant variant.Variant
|
||||
pcrs measurements.M
|
||||
idKeyConfig config.SNPFirmwareSignerConfig
|
||||
validator atls.Validator
|
||||
log debugLog
|
||||
}
|
||||
|
||||
// NewValidator creates a new Validator.
|
||||
func NewValidator(conf *config.Config, maaURL string, log debugLog) (*Validator, error) {
|
||||
v := Validator{log: log}
|
||||
attestVariant, err := variant.FromString(conf.AttestationVariant)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("parsing attestation variant: %w", err)
|
||||
}
|
||||
v.attestationVariant = attestVariant // valid variant
|
||||
|
||||
if err := v.setPCRs(conf); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if v.attestationVariant.Equal(variant.AzureSEVSNP{}) {
|
||||
v.idKeyConfig = config.SNPFirmwareSignerConfig{
|
||||
AcceptedKeyDigests: conf.Provider.Azure.IDKeyDigest,
|
||||
EnforcementPolicy: conf.IDKeyDigestPolicy(),
|
||||
MAAURL: maaURL,
|
||||
}
|
||||
}
|
||||
|
||||
return &v, nil
|
||||
func NewValidator(cmd *cobra.Command, config config.AttestationCfg, log debugLog) (atls.Validator, error) {
|
||||
return choose.Validator(config, warnLogger{cmd: cmd, log: log})
|
||||
}
|
||||
|
||||
// UpdateInitPCRs sets the owner and cluster PCR values.
|
||||
func (v *Validator) UpdateInitPCRs(ownerID, clusterID string) error {
|
||||
if err := v.updatePCR(uint32(measurements.PCRIndexOwnerID), ownerID); err != nil {
|
||||
func UpdateInitPCRs(config config.AttestationCfg, ownerID, clusterID string) error {
|
||||
m := config.GetMeasurements()
|
||||
if err := updatePCR(m, uint32(measurements.PCRIndexOwnerID), ownerID); err != nil {
|
||||
return err
|
||||
}
|
||||
return v.updatePCR(uint32(measurements.PCRIndexClusterID), clusterID)
|
||||
return updatePCR(m, uint32(measurements.PCRIndexClusterID), clusterID)
|
||||
}
|
||||
|
||||
// updatePCR adds a new entry to the measurements of v, or removes the key if the input is an empty string.
|
||||
|
@ -67,9 +38,9 @@ func (v *Validator) UpdateInitPCRs(ownerID, clusterID string) error {
|
|||
// When adding, the input is first decoded from hex or base64.
|
||||
// We then calculate the expected PCR by hashing the input using SHA256,
|
||||
// appending expected PCR for initialization, and then hashing once more.
|
||||
func (v *Validator) updatePCR(pcrIndex uint32, encoded string) error {
|
||||
func updatePCR(m measurements.M, pcrIndex uint32, encoded string) error {
|
||||
if encoded == "" {
|
||||
delete(v.pcrs, pcrIndex)
|
||||
delete(m, pcrIndex)
|
||||
return nil
|
||||
}
|
||||
|
||||
|
@ -85,42 +56,15 @@ func (v *Validator) updatePCR(pcrIndex uint32, encoded string) error {
|
|||
// new_pcr_value := hash(old_pcr_value || data_to_extend)
|
||||
// Since we use the TPM2_PCR_Event call to extend the PCR, data_to_extend is the hash of our input
|
||||
hashedInput := sha256.Sum256(decoded)
|
||||
oldExpected := v.pcrs[pcrIndex].Expected
|
||||
oldExpected := m[pcrIndex].Expected
|
||||
expectedPcr := sha256.Sum256(append(oldExpected[:], hashedInput[:]...))
|
||||
v.pcrs[pcrIndex] = measurements.Measurement{
|
||||
m[pcrIndex] = measurements.Measurement{
|
||||
Expected: expectedPcr,
|
||||
ValidationOpt: v.pcrs[pcrIndex].ValidationOpt,
|
||||
ValidationOpt: m[pcrIndex].ValidationOpt,
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (v *Validator) setPCRs(config *config.Config) error {
|
||||
measurements := config.GetMeasurements()
|
||||
if len(measurements) == 0 {
|
||||
return errors.New("no measurements found in config")
|
||||
}
|
||||
v.pcrs = measurements
|
||||
return nil
|
||||
}
|
||||
|
||||
// V returns the validator as atls.Validator.
|
||||
func (v *Validator) V(cmd *cobra.Command) atls.Validator {
|
||||
v.updateValidator(cmd)
|
||||
return v.validator
|
||||
}
|
||||
|
||||
// PCRS returns the validator's PCR map.
|
||||
func (v *Validator) PCRS() measurements.M {
|
||||
return v.pcrs
|
||||
}
|
||||
|
||||
func (v *Validator) updateValidator(cmd *cobra.Command) {
|
||||
log := warnLogger{cmd: cmd, log: v.log}
|
||||
|
||||
// Use of a valid variant has been check in NewValidator so we may drop the error
|
||||
v.validator, _ = choose.Validator(v.attestationVariant, v.pcrs, v.idKeyConfig, log)
|
||||
}
|
||||
|
||||
// warnLogger implements logging of warnings for validators.
|
||||
type warnLogger struct {
|
||||
cmd *cobra.Command
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue