| // Copyright 2018 The Fuchsia Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| library fuchsia.kms; |
| |
| using fuchsia.mem as mem; |
| |
| const MAX_KEY_NAME_SIZE uint8 = 32; |
| const MAX_DATA_SIZE uint32 = 65536; |
| |
| type Error = strict enum { |
| /// Internal unexpected error. |
| INTERNAL_ERROR = 1; |
| /// When trying to create/import a new key but a key with the same name already exists. |
| KEY_ALREADY_EXISTS = 2; |
| /// When the key you are trying to use is not found. |
| KEY_NOT_FOUND = 3; |
| /// When the key material could not be parsed. |
| PARSE_KEY_ERROR = 4; |
| /// When the size for input data is larger than `MAX_DATA_SIZE`. |
| INPUT_TOO_LARGE = 5; |
| }; |
| |
| type AsymmetricKeyAlgorithm = strict enum { |
| RSA_SSA_PSS_SHA256_2048 = 1; |
| RSA_SSA_PSS_SHA256_3072 = 2; |
| RSA_SSA_PSS_SHA512_4096 = 3; |
| RSA_SSA_PKCS1_SHA256_2048 = 4; |
| RSA_SSA_PKCS1_SHA256_3072 = 5; |
| RSA_SSA_PKCS1_SHA512_4096 = 6; |
| ECDSA_SHA256_P256 = 7; |
| ECDSA_SHA512_P384 = 8; |
| ECDSA_SHA512_P521 = 9; |
| }; |
| |
| type KeyOrigin = strict enum { |
| /// The key was generated in this KMS instance. |
| GENERATED = 1; |
| /// The key was imported. |
| IMPORTED = 2; |
| }; |
| |
| type KeyProvider = strict enum { |
| /// A mock provider only used for unit testing. |
| MOCK_PROVIDER = 1; |
| /// A software provider that uses rust AesGcm trait for symmetric key operation and mundane for |
| /// asymmetric key operation. |
| SOFTWARE_PROVIDER = 2; |
| /// A software provider that only supports mundane-based asymmetric key operation. |
| SOFTWARE_ASYMMETRIC_ONLY_PROVIDER = 3; |
| /// A crypto provider based on Keysafe Trusted App in OPTEE. |
| OPTEE_PROVIDER = 4; |
| }; |
| |
| type Signature = struct { |
| bytes bytes:512; |
| }; |
| |
| type PublicKey = struct { |
| bytes bytes:256; |
| }; |
| |
| @discoverable |
| protocol KeyManager { |
| /// Seal data to an encrypted form. |
| /// |
| /// Seal data to an encrypted form. The sealed data can only be unsealed by the same KMS instance |
| /// by using UnsealData. `plain_text` needs to be less than `MAX_DATA_SIZE` bytes. |
| SealData(resource struct { |
| plain_text mem.Buffer; |
| }) -> (resource struct { |
| cipher_text mem.Buffer; |
| }) error Error; |
| |
| /// Unseal sealed data. |
| /// |
| /// Unseal data previously sealed by this KMS instance. |
| UnsealData(resource struct { |
| cipher_text mem.Buffer; |
| }) -> (resource struct { |
| plain_text mem.Buffer; |
| }) error Error; |
| |
| /// Generate an asymmetric key. |
| /// |
| /// Generate an asymmetric key using `key_name` as the unique name. `key` is the generated |
| /// asymmetric key interface request. If the `key_name` is not unique, you would get |
| /// `KEY_ALREADY_EXISTS`. The generated key can be used to sign data. The algorithm used for |
| /// generating asymmetric key is `ECDSA_SHA512_P521`. |
| GenerateAsymmetricKey(resource struct { |
| key_name string:MAX_KEY_NAME_SIZE; |
| key server_end:AsymmetricPrivateKey; |
| }) -> (struct {}) error Error; |
| |
| /// Generate an asymmetric key with a specific algorithm. |
| /// |
| /// Generate an asymmetric key using `key_name` as the unique name and `key_algorithm` as |
| /// algorithm. `key` is the generated asymmetric key interface request. If the `key_name` is not |
| /// unique, you would get `KEY_ALREADY_EXISTS`. |
| GenerateAsymmetricKeyWithAlgorithm(resource struct { |
| key_name string:MAX_KEY_NAME_SIZE; |
| key_algorithm AsymmetricKeyAlgorithm; |
| key server_end:AsymmetricPrivateKey; |
| }) -> (struct {}) error Error; |
| |
| /// Import an asymmetric private key with a specific algorithm. |
| /// |
| /// Import an asymmetric private key using `key_name` as the unique name, `key_algorithm` as |
| /// algorithm and `data` as key data. `key` is imported asymmetric key interface request. Key |
| /// data should be in asn.1 encoded DER format. If the `key_name` is not unique, you would get |
| /// `KEY_ALREADY_EXISTS`. |
| ImportAsymmetricPrivateKey(resource struct { |
| data bytes; |
| key_name string:MAX_KEY_NAME_SIZE; |
| key_algorithm AsymmetricKeyAlgorithm; |
| key server_end:AsymmetricPrivateKey; |
| }) -> (struct {}) error Error; |
| |
| /// Get an asymmetric private key handle. |
| /// |
| /// Get an asymmetric private key handle using the `key_name`. If such key is not found, would |
| /// return `KEY_NOT_FOUND`. |
| GetAsymmetricPrivateKey(resource struct { |
| key_name string:MAX_KEY_NAME_SIZE; |
| key server_end:AsymmetricPrivateKey; |
| }) -> (struct {}) error Error; |
| |
| /// Delete a key. |
| /// |
| /// Delete a key for `key_name`. For all the current handle to the deleted key, they would |
| /// become invalid and all following requests on those handles would return `KEY_NOT_FOUND`, user |
| /// should close the invalid handles once get `KEY_NOT_FOUND` error. |
| DeleteKey(struct { |
| key_name string:MAX_KEY_NAME_SIZE; |
| }) -> (struct {}) error Error; |
| }; |
| |
| protocol Key { |
| /// Get the key origin (generated/imported). |
| GetKeyOrigin() -> (struct { |
| key_origin KeyOrigin; |
| }) error Error; |
| |
| /// Get the name for the crypto provider backing up the key. |
| GetKeyProvider() -> (struct { |
| key_provider KeyProvider; |
| }) error Error; |
| }; |
| |
| protocol AsymmetricPrivateKey { |
| compose Key; |
| |
| /// Sign `data` using the current key. `data` needs to be less than `MAX_DATA_SIZE` bytes. |
| Sign(resource struct { |
| data mem.Buffer; |
| }) -> (struct { |
| signature Signature; |
| }) error Error; |
| /// Get the DER format public key for the current private key. |
| GetPublicKey() -> (struct { |
| public_key PublicKey; |
| }) error Error; |
| /// Get the key algorithm. |
| GetKeyAlgorithm() -> (struct { |
| key_algorithm AsymmetricKeyAlgorithm; |
| }) error Error; |
| }; |