package apiv1 import ( "crypto" "crypto/x509" "strings" "github.com/pkg/errors" ) // KeyManager is the interface implemented by all the KMS. type KeyManager interface { GetPublicKey(req *GetPublicKeyRequest) (crypto.PublicKey, error) CreateKey(req *CreateKeyRequest) (*CreateKeyResponse, error) CreateSigner(req *CreateSignerRequest) (crypto.Signer, error) Close() error } // Decrypter is an interface implemented by KMSes that are used // in operations that require decryption type Decrypter interface { CreateDecrypter(req *CreateDecrypterRequest) (crypto.Decrypter, error) } // CertificateManager is the interface implemented by the KMS that can load and // store x509.Certificates. type CertificateManager interface { LoadCertificate(req *LoadCertificateRequest) (*x509.Certificate, error) StoreCertificate(req *StoreCertificateRequest) error } // ErrNotImplemented is the type of error returned if an operation is not // implemented. type ErrNotImplemented struct { Message string } func (e ErrNotImplemented) Error() string { if e.Message != "" { return e.Message } return "not implemented" } // ErrAlreadyExists is the type of error returned if a key already exists. This // is currently only implmented on pkcs11. type ErrAlreadyExists struct { Message string } func (e ErrAlreadyExists) Error() string { if e.Message != "" { return e.Message } return "key already exists" } // Type represents the KMS type used. type Type string const ( // DefaultKMS is a KMS implementation using software. DefaultKMS Type = "" // SoftKMS is a KMS implementation using software. SoftKMS Type = "softkms" // CloudKMS is a KMS implementation using Google's Cloud KMS. CloudKMS Type = "cloudkms" // AmazonKMS is a KMS implementation using Amazon AWS KMS. AmazonKMS Type = "awskms" // PKCS11 is a KMS implementation using the PKCS11 standard. PKCS11 Type = "pkcs11" // YubiKey is a KMS implementation using a YubiKey PIV. YubiKey Type = "yubikey" // SSHAgentKMS is a KMS implementation using ssh-agent to access keys. SSHAgentKMS Type = "sshagentkms" ) // Options are the KMS options. They represent the kms object in the ca.json. type Options struct { // The type of the KMS to use. Type string `json:"type"` // Path to the credentials file used in CloudKMS and AmazonKMS. CredentialsFile string `json:"credentialsFile"` // URI is based on the PKCS #11 URI Scheme defined in // https://tools.ietf.org/html/rfc7512 and represents the configuration used // to connect to the KMS. // // Used by: pkcs11 URI string `json:"uri"` // Pin used to access the PKCS11 module. It can be defined in the URI using // the pin-value or pin-source properties. Pin string `json:"pin"` // ManagementKey used in YubiKeys. Default management key is the hexadecimal // string 010203040506070801020304050607080102030405060708: // []byte{ // 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, // 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, // 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, // } ManagementKey string `json:"managementKey"` // Region to use in AmazonKMS. Region string `json:"region"` // Profile to use in AmazonKMS. Profile string `json:"profile"` } // Validate checks the fields in Options. func (o *Options) Validate() error { if o == nil { return nil } switch Type(strings.ToLower(o.Type)) { case DefaultKMS, SoftKMS: // Go crypto based kms. case CloudKMS, AmazonKMS, SSHAgentKMS: // Cloud based kms. case YubiKey, PKCS11: // Hardware based kms. default: return errors.Errorf("unsupported kms type %s", o.Type) } return nil }