1 | /* Copyright 2015 OpenMarket Ltd |
2 | * |
3 | * Licensed under the Apache License, Version 2.0 (the "License"); |
4 | * you may not use this file except in compliance with the License. |
5 | * You may obtain a copy of the License at |
6 | * |
7 | * http://www.apache.org/licenses/LICENSE-2.0 |
8 | * |
9 | * Unless required by applicable law or agreed to in writing, software |
10 | * distributed under the License is distributed on an "AS IS" BASIS, |
11 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
12 | * See the License for the specific language governing permissions and |
13 | * limitations under the License. |
14 | */ |
15 | |
16 | #ifndef OLM_CIPHER_H_ |
17 | #define OLM_CIPHER_H_ |
18 | |
19 | #include <stdint.h> |
20 | #include <stdlib.h> |
21 | |
22 | // Note: exports in this file are only for unit tests. Nobody else should be |
23 | // using this externally |
24 | #include "olm/olm_export.h" |
25 | |
26 | #ifdef __cplusplus |
27 | extern "C" { |
28 | #endif |
29 | |
30 | struct _olm_cipher; |
31 | |
32 | struct _olm_cipher_ops { |
33 | /** |
34 | * Returns the length of the message authentication code that will be |
35 | * appended to the output. |
36 | */ |
37 | size_t (*mac_length)(const struct _olm_cipher *cipher); |
38 | |
39 | /** |
40 | * Returns the length of cipher-text for a given length of plain-text. |
41 | */ |
42 | size_t (*encrypt_ciphertext_length)( |
43 | const struct _olm_cipher *cipher, |
44 | size_t plaintext_length |
45 | ); |
46 | |
47 | /* |
48 | * Encrypts the plain-text into the output buffer and authenticates the |
49 | * contents of the output buffer covering both cipher-text and any other |
50 | * associated data in the output buffer. |
51 | * |
52 | * |---------------------------------------output_length-->| |
53 | * output |--ciphertext_length-->| |---mac_length-->| |
54 | * ciphertext |
55 | * |
56 | * The plain-text pointers and cipher-text pointers may be the same. |
57 | * |
58 | * Returns size_t(-1) if the length of the cipher-text or the output |
59 | * buffer is too small. Otherwise returns the length of the output buffer. |
60 | */ |
61 | size_t (*encrypt)( |
62 | const struct _olm_cipher *cipher, |
63 | uint8_t const * key, size_t key_length, |
64 | uint8_t const * plaintext, size_t plaintext_length, |
65 | uint8_t * ciphertext, size_t ciphertext_length, |
66 | uint8_t * output, size_t output_length |
67 | ); |
68 | |
69 | /** |
70 | * Returns the maximum length of plain-text that a given length of |
71 | * cipher-text can contain. |
72 | */ |
73 | size_t (*decrypt_max_plaintext_length)( |
74 | const struct _olm_cipher *cipher, |
75 | size_t ciphertext_length |
76 | ); |
77 | |
78 | /** |
79 | * Authenticates the input and decrypts the cipher-text into the plain-text |
80 | * buffer. |
81 | * |
82 | * |----------------------------------------input_length-->| |
83 | * input |--ciphertext_length-->| |---mac_length-->| |
84 | * ciphertext |
85 | * |
86 | * The plain-text pointers and cipher-text pointers may be the same. |
87 | * |
88 | * Returns size_t(-1) if the length of the plain-text buffer is too |
89 | * small or if the authentication check fails. Otherwise returns the length |
90 | * of the plain text. |
91 | */ |
92 | size_t (*decrypt)( |
93 | const struct _olm_cipher *cipher, |
94 | uint8_t const * key, size_t key_length, |
95 | uint8_t const * input, size_t input_length, |
96 | uint8_t const * ciphertext, size_t ciphertext_length, |
97 | uint8_t * plaintext, size_t max_plaintext_length |
98 | ); |
99 | }; |
100 | |
101 | struct _olm_cipher { |
102 | const struct _olm_cipher_ops *ops; |
103 | /* cipher-specific fields follow */ |
104 | }; |
105 | |
106 | struct _olm_cipher_aes_sha_256 { |
107 | struct _olm_cipher base_cipher; |
108 | |
109 | /** context string for the HKDF used for deriving the AES256 key, HMAC key, |
110 | * and AES IV, from the key material passed to encrypt/decrypt. |
111 | */ |
112 | uint8_t const * kdf_info; |
113 | |
114 | /** length of context string kdf_info */ |
115 | size_t kdf_info_length; |
116 | }; |
117 | |
118 | OLM_EXPORT extern const struct _olm_cipher_ops _olm_cipher_aes_sha_256_ops; |
119 | |
120 | /** |
121 | * get an initializer for an instance of struct _olm_cipher_aes_sha_256. |
122 | * |
123 | * To use it, declare: |
124 | * |
125 | * struct _olm_cipher_aes_sha_256 MY_CIPHER = |
126 | * OLM_CIPHER_INIT_AES_SHA_256("MY_KDF"); |
127 | * struct _olm_cipher *cipher = OLM_CIPHER_BASE(&MY_CIPHER); |
128 | */ |
129 | #define OLM_CIPHER_INIT_AES_SHA_256(KDF_INFO) { \ |
130 | /*.base_cipher = */{ &_olm_cipher_aes_sha_256_ops },\ |
131 | /*.kdf_info = */(uint8_t *)(KDF_INFO), \ |
132 | /*.kdf_info_length = */sizeof(KDF_INFO) - 1 \ |
133 | } |
134 | #define OLM_CIPHER_BASE(CIPHER) \ |
135 | (&((CIPHER)->base_cipher)) |
136 | |
137 | |
138 | #ifdef __cplusplus |
139 | } /* extern "C" */ |
140 | #endif |
141 | |
142 | #endif /* OLM_CIPHER_H_ */ |
143 | |